9

Everytime I compile and run c file, I have to type:

gcc filename.c

a.out

I don't want to do this in two lines, How to compile and run in one line on linux terminal?

online.0227
  • 640
  • 4
  • 15
  • 29

5 Answers5

16

Try

gcc filename.c && a.out

It only runs the second command if the first was successful. See https://askubuntu.com/questions/334994/which-one-is-better-using-or-to-execute-multiple-commands-in-one-line

Community
  • 1
  • 1
user3413723
  • 11,147
  • 6
  • 55
  • 64
  • One problem with this is that the program may compile, with warnings, and then run without giving the user a chance to inspect the warnings. See my answer below. – ad absurdum Jan 26 '17 at 14:23
5

The Quick and Dirty Solution is Wrong

The quick and dirty solution is a very bad idea in C:

gcc myfile.c && ./a.out

This will not run the executable if the compilation fails, but when compilation succeeds the code will automatically run even if warnings are issued; in C you should always at least inspect warnings before attempting to run code. For the most part you should just never run code that compiles with warnings. Often running code with warnings will mean that code has some undefined behavior; you should not be running such blindly. Of course, with warnings at a minimum as in the above code, there may not be a lot of warnings, when there should be, anyway. At the absolute minimum, one should use:

gcc myfile.c -Wall -Wextra -Werror && ./a.out

Using -Wall -Wextra will issue warnings for a lot of silly mistakes that bring the undefined behavior, and -Werror keeps code compiled with warnings from automatically running.

A Better Solution

To solve this problem, and type less, I used to use this bash script saved as crepl in my search path:

#!/bin/bash
gcc -std=c99 -Wall -Wextra -Wpedantic -Werror $1 -o tempout &&\
    ./tempout && rm tempout

When I wanted to quickly test some source code saved in, e.g., myfile.c, I could enter at the command-line:

crepl myfile.c

The code will not run if compilation fails, and it will not run if it compiles with warnings thanks to -Werror. If compilation is successful, the program runs, and the temporary executable is removed after running.

Improvements

Since originally writing this answer I have evolved my solution into a slightly fancier bash script that accepts optional further arguments to the compiler, linking libraries, etc.

#!/usr/bin/env bash
# crun
#
# A script to invoke gcc, build the executable, execute the binary,
# and cleanup after. The script will exit without running the executable
# if there are any compiler errors or warnings.
#
# This script uses -std=c18, but it could probably be modified so that
# the version is taken from a command-line parameter, defaulting to c18.
#
# Any commands following the crun invocation are appended to CMD.
CMD="gcc -std=c18 -Wall -Wextra -Wpedantic -Werror"
TEMPFILE="tempfile$$"
for ARG in "$@"
do
    CMD+=" $ARG"
done
CMD+=" -o ${TEMPFILE} && ./${TEMPFILE} && rm ${TEMPFILE}"

eval $CMD

Now if I need to link in, e.g., the math library:

crun myfile.c -lm

does the trick, failing if there are any errors or warnings (which are turned up to reasonable levels), and cleaning up after itself.

ad absurdum
  • 19,498
  • 5
  • 37
  • 60
4

You can separate commands with a ;. So for example:

gcc filename.c; ./a.out

However, you probably only want to run a.out if the compile was successful. For this you can use &&:

gcc filename.c && ./a.out
melpomene
  • 84,125
  • 8
  • 85
  • 148
gerowam
  • 383
  • 1
  • 11
1

Explanation:

A ; B – Run A and then B, regardless of the success or failure of A

A && B – Run B only if A succeeded

A || B – Run B only if A failed

1

You wanted how to compile and run. I give you how to write, compile and run.

cat << EOF > temp.c && gcc temp.c ; ./a.out ; rm temp.c a.out
#include <stdio.h>
int main(){ printf("%s\n", "Hello World!"); return 0; }
EOF

If you use such a thing fairly regularly you might also be interested in this:

#!/bin/sh
# GCC in the streams

temp="temp.c"

sgcc() {
    (
        rm "$temp" # just to be sure
        # append every line from shell to the temp file
        while read -r l; do printf "%s\n" "$l" >>"$temp"; done
        cat "$temp"
        gcc "$temp"
        exitcode=$?
        ./a.out
        rm "$temp" a.out
        exit $exitcode
    )
}

Which you can call like below:

sgcc << EOF
#include <stdio.h>
int main(){ printf("%s\n", "Hello World!"); return 0; }
EOF
Davoodeh
  • 69
  • 1
  • 5