Como manipular dois argumentos possíveis?

0

Eu uso meu script personalizado cccpara compilar .carquivos como este:

g++ -std=c++11 -Wall -pedantic -Wno-long-long -Wshadow -g -o "${1%%.c}.out" -lm "$1"

Basicamente eu uso ccc main.ce depois main.outsai. Agora eu também quero compilar .cpparquivos usando o mesmo script. Até agora eu tenho isso:

#!/bin/bash

if [ "$1" == "*.cpp" ]; then
    g++ -std=c++11 -Wall -pedantic -Wno-long-long -Wshadow -g -o "${1%%.cpp}.out" -lm "$1"
    echo "g++ -std=c++11 -Wall -pedantic -Wno-long-long -Wshadow -g -o ${1%%}.out -lm $1"
elif [ "$1" == "*.c" ]; then
    g++ -std=c++11 -Wall -pedantic -Wno-long-long -Wshadow -g -o "${1%%.c}.out" -lm "$1"
    echo "g++ -std=c++11 -Wall -pedantic -Wno-long-long -Wshadow -g -o ${1%%}.out -lm $1"
else
    echo "Error - file does not exist or wrong type"
fi

No entanto, agora ambos .cppe .carquivos não conseguem compilar e meu errmsg é ecoado. Qual foi o meu erro?

Hichigaya Hachiman
fonte
Você deveria estar realmente usando makeisso ...
xenoid
Eu não estou familiarizado com makemuito, mas eu não teria que criar um makefile para cada projeto então?
Hichigaya Hachiman
Sim, mas: 1) um makefile pode incluir outros makefiles, 2) makefile dá regras (como como passar de .cpp para .o, geralmente comuns a muitos projetos) e dependências (que podem ser a única coisa que você tem que escrever Mesmo que o make muitas vezes descubra as dependências, makeele foi a ferramenta de construção escolhida por mais de 40 anos para os desenvolvedores de C / C ++. A página da Wikipedia oferece uma boa idéia de como isso funciona
xenoid

Respostas:

0

Seus testes if não estão verificando arquivos * .c e * .cpp, eles estão verificando se o argumento é literalmente "* .cpp" ou "* .c".

Tente isso para ver suas condições acionadas:
ccc "*.cpp"
ccc "*.c"

Com base neste post , vejo que você pode obter o comportamento desejado, removendo as aspas em torno do "* .cpp" e adicionando um par extra de colchetes:
if [[ "$1" == *.cpp ]]; then

Geoff Gustafson
fonte
0

Seus operadores de comparação não estão se concentrando da maneira como você acha que eles estão se globbing.

Quando você verifica =="*.c"ou =="*.cpp"está verificando se corresponde a essa cadeia real.

O que você quer é a comparação de expressões regulares.

if [[ $1 =~ $regex ]]; then

Para a expressão regular real, o caractere ^indica "começa com" e $indica "termina com", então

if [[ $1 =~ ^[a-zA-Z0-9]*\.cpp$ ]]; then

pode ser um bom começo para verificar arquivos cpp e

if [[ $1 =~ ^[a-zA-Z0-9]*\.c$ ]]; then

para arquivos c.

A única habilidade que eu recomendo fortemente para quem é um administrador de sistema (especialmente em um sistema * nix) ou qualquer tipo de script / programação / desenvolvimento é aprender a usar expressões regulares. Há muito poucos tutoriais e cheat-sheets por aí, aqui está o primeiro da minha coleção de marcadores - https://www.maketecheasier.com/regular-expressions-cheat-sheet/

ivanivan
fonte