2012-03-08 7 views
7

voglio scrivere qualcosa in queste righe:GNU Make ciclo for con due variabili

$(foreach (var1, var2), ($(LIST1), $(LIST2)), cp $(var1) $(var2);) 

Come faccio a fare questo in un makefile GNU?

+0

All'interno di una regola, o fuori? – Beta

+0

All'interno di una regola - –

+0

Anche mentre sto scrivendo questa cosa alla lunga ho capito che ne avrò bisogno al di fuori di una regola. –

risposta

8

di Beta da utilizzare join è sulla strada giusta, ma il problema è che non è così facile da usare in un modo che costruisce una riga di comando che contiene spazi bianchi, come ad esempio quella che in origine voleva:

$(foreach (var1, var2), ($(LIST1), $(LIST2)), cp $(var1) $(var2);) 

perché join unisce le parole insieme: originariamente era destinato alla costruzione di nomi di file. Comunque puoi giocare un trucco; ecco un esempio di un modo per utilizzare join che ti dà l'output che stai cercando:

$(subst ^, ,$(join $(addprefix cp^,$(LIST1)),$(patsubst %,^%;,$(LIST2)))) 

Se pensate che le vostre liste possono contenere caratteri ^ quindi scegliere qualcos'altro. Fatemi sapere se avete bisogno di questo scompattato/spiegato.

+0

Questo ha funzionato per me in base alla domanda sopra. –

2
LIST1 := a b c 
LIST2 := 1 2 3 

# outside a rule: 
$(foreach var1, a b c, $(foreach var2, 1 2 3, $(info $(var1)_$(var2)))) 

# inside a rule: first line starts with a TAB, all the rest are spaces 
all: 
    @for x in $(LIST1);\ 
    do \ 
     for y in $(LIST2);\ 
     do\ 
     echo $$x $$y; \ 
     done \ 
    done 

(Si prega di notare che un ciclo nidificato che fa cp non ha molto senso.)

EDIT:
Bene perché non l'hai detto subito? suggerimento

LIST3 := $(join $(LIST1),$(LIST2)) 
+1

Sì perché non desidero il prodotto incrociato Ho bisogno di un mapping uno a uno. Questo è ciò che ha il cervello che va in loop. –

+0

Sooooo ... hai contrassegnato questa risposta come corretta. Non sembra rispondere alla domanda che hai avuto però. E 'questo quello che volevi o no? – MadScientist

+0

Questa non è la risposta che volevo, ma nessuno ha risposto dopo alcuni giorni, quindi l'ho contrassegnato come la risposta più relativamente corretta. Se hai una risposta migliore per favore posta. –

0

Questo è un buon candidato per gsml (libreria standard GNU). Puoi includerlo inserendo i file __gmsl e gml nella directory corrente (o in /usr/gnu/include, /usr/local/include/ ecc.) E aggiungendo la riga include gsml nel tuo Makefile. Include la funzione pairmap, che fa esattamente ciò che desideri (ad esempio zipWith).

include gmsl 
cp2 = cp $1 $2; 
zip = $1 : $2 
$(LIST2): 
    @echo $(call pairmap, zip, $(LIST1), $(LIST2)) 
    $(call pairmap, cp2, $(LIST1), $(LIST2)) 

uscite

$ make 
A : 1 B : 2 C : 3 D : 4 
cp A 1; cp B 2; cp C 3; cp D 4;