Fórum Root.cz

Hlavní témata => Vývoj => Téma založeno: filip.z 11. 02. 2013, 16:48:24

Název: Bash a vícenásobné předávání proměnných
Přispěvatel: filip.z 11. 02. 2013, 16:48:24
Ahoj,

chci se zeptat ohledně bashe a předávání proměnných funkcím přes poziční parametry.

Moje blíže nespecifikovaná funkce ( funkce_1 ) je volána s několika parametry, z nichž některý může být i hvězdička.
V takové případě musím při volání této funkce hvězdičku obalit apostrofy, uvozovkami či předsadit zpětným lomítkem.

Tedy např.:

Kód: [Vybrat]
funkce_1 prvni_argument \* treti_argument

Potud je vše v pořádku.

Pak ale následuje další funkce ( funkce_2 ) která zavolá funkci_1 pro každý svůj argument.

Tedy:

Kód: [Vybrat]
funkce_2 () {

  while [ $# "= 0 ]; do

    funkce_1 $1
    shift

  done

}

A tady nastává problém:

Zde je příklad volání funkce_2 se dvěma způsoby zadání argumentů, z nichž ani jeden nedělá to, co bych potřeboval:

Kód: [Vybrat]
funkce_2 "prvni_argument * druhy_argument" "prvni_argument \* treti_argument"

Funkce_2 zavolá pro svůj první parametr funkci_1 s argumenty : prvni_argument, místo hvězdičky jména souborů aktuálního adresáře a treti_argument.

Jenže já tam chci tu hvězdičku.
Domníval jsem se, že pokud před ni dám lomítko, že tam hvězdička zůstane - viz druhý argument funkce_2.
Zůstala, jenže i s lomítkem. Totéž i pro apostrofy a uvozovky. A já bych rád právě a jenom hvězdičku.

Pokud někdo pochopíte můj problém, budu rád, pokud mi sdělíte svůj názor, případně vysvětlíte kde je problém nebo co chápu špatně.
Díky.



Název: Re:bash - několikanásobné předávání proměnných ve funkcích
Přispěvatel: Martin Volf 11. 02. 2013, 19:37:12
nezabralo by:
Kód: [Vybrat]
funkce_1 "$1"?
Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: aaa158 11. 02. 2013, 21:45:28
pomohlo.

http://tldp.org/LDP/abs/html/quotingvar.html
Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: filipz 12. 02. 2013, 09:38:22
Myslím, že to nic nevyřeší, pokud to chápu správně.
Zdrojový soubor:
Kód: [Vybrat]
funkce_1 () {
  for a in $1; do
    echo "$a"
  done
}

funkce_2 () {
  while [ $# != 0 ]; do
    funkce_1 "$1"
    shift
  done
}

Řekl bych, že problém bude v pořadí kroků, v jakých interpret skript zpracovává.
Tedy že detekce znaků rušících význam spec. znaků ( tedy detekce '\' před '*' ) proběhne dříve než dosazení hodnoty proměnné, kdežto náhrada jmen souborů až po něm.
Což by sice problém neřešilo, ale vysvětlilo.

Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: Jakub Neburka 12. 02. 2013, 13:32:59
Mě to spíš připadá, že problém je v návrhu.. proč vůbec ten parametr funkci funkce_1 potřebujete escapovat, když v jejím volání necháte shell ho rozexpandovat? Napište přesněji, čeho chcete dosáhnout a možná dostanete cenější rady ;]
Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: aaa158 12. 02. 2013, 13:40:16
Myslím, že to nic nevyřeší, pokud to chápu správně.
Zdrojový soubor:
Kód: [Vybrat]
funkce_1 () {
  for a in $1; do
    echo "$a"
  done
}

funkce_2 () {
  while [ $# != 0 ]; do
    funkce_1 "$1"
    shift
  done
}

Řekl bych, že problém bude v pořadí kroků, v jakých interpret skript zpracovává.
Tedy že detekce znaků rušících význam spec. znaků ( tedy detekce '\' před '*' ) proběhne dříve než dosazení hodnoty proměnné, kdežto náhrada jmen souborů až po něm.
Což by sice problém neřešilo, ale vysvětlilo.

skus:

Kód: [Vybrat]
funkce_1 () {
  for a in "$1"; do
...
Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: Milan Straka 12. 02. 2013, 14:00:27
Citace
Řekl bych, že problém bude v pořadí kroků, v jakých interpret skript zpracovává.
Tedy že detekce znaků rušících význam spec. znaků ( tedy detekce '\' před '*' ) proběhne dříve než dosazení hodnoty proměnné, kdežto náhrada jmen souborů až po něm.
Což by sice problém neřešilo, ale vysvětlilo.

Cely ten postup quotingu, parameter expansion a pathname expansion je docela zasmodrchany, detaily viz sekce QUOTING a EXPANSION v man bash.

Nicmene by Ti mohlo pomoci "set -f" a "set +f". Tim se zastavuje ("set -f") a opet povoluje ("set +f") pathname expansion, tj. nahrazeni hvezdicek, ? a [] za nazvy souboru.
Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: filipz 12. 02. 2013, 14:36:56
Díky,

nenapadlo mě, že si to nahrazování můžu nějak vypnout či přenastavit, to je určitě účinnější než zjišťovat, jak ten proces zpracování cmd funguje.

set -/+f to celé řeší.

Díky všem za odpovědi.
Název: Re:Bash a vícenásobné předávání proměnných
Přispěvatel: filipz 12. 02. 2013, 15:04:46
Kód: [Vybrat]
  for a in $1; do
    echo "$a"
  done
}

funkce_2 () {
  while [ $# != 0 ]; do
    funkce_1 "$1"
    shift
  done
}

Omlouvám se, toto skutečně pomůže.
Mám momentálně 2 stroje, na jednom internet a na druhém linux :-\ , při testování jsem zapoměl uvozovky u echo "$a" a '*' se expandovala až při výpisu.
Každopádně set -+f poznatek navíc, díky ;-)