Come posso sopprimere lo spazio tra gli argomenti generati durante l'espansione del controvento?


8

Ho usato il seguente comando per creare un elenco di URL che voglio testare:

echo -e localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload}"\n" >> urls.txt

Sfortunatamente gli URL aggiunti a urls.txtciascuno avevano uno spazio davanti a loro (tranne che per il primo, ovviamente). Capisco perché è successo e mi rendo conto che potrei semplicemente toglierlo mandando in bocca sedun'espressione, ma mi piacerebbe sapere se c'è un modo per sopprimerlo invece. (Può sembrare sciocco e pedante, ma non è diverso dalla preferenza che così tante persone provano per non "abusare dei gatti" .)

Ho provato a fare due virgolette per sopprimere la suddivisione delle parole , ma questo ha soppresso anche l'espansione del controvento, quindi è stato un no-go.

Ho provato a cambiare IFS in una stringa vuota, ma non ha funzionato neanche:

IFS='' echo -e localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload}"\n" >> urls.txt

Né lo ha cambiato in una nuova riga:

IFS='\n' echo -e localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload}"\n" >> urls.txt

Stai usando bash o zsh?
— Braiam,

al momento sto usando bash (sono al lavoro) ma sul mio laptop uso zsh. Mi aspettavo che l'espansione del supporto funzionasse in modo identico in entrambi, ma forse non è così.
— iconoclasta,

In tal caso, la risposta di Gnouc sarà la più compatibile con diverse shell.
— Braiam,

La risposta di Richard non sarebbe ugualmente compatibile? (Ha anche il vantaggio di essere più semplice, quindi non devo fermarmi a pensare alle cose difficili la prossima volta che voglio usarlo.) D'altra parte, anche la risposta di Gnouc è eccellente. E penso di aver imparato di più dalla risposta di Glenn Jackson. La risposta di Leiaz sembra più semplice ed elegante, ma ovviamente è solo zsh.
— iconoclasta,

Risposte:


8

È possibile memorizzare l'espansione del controvento in un array, quindi emetterlo nel modo desiderato:

urls=( localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload} )

Poi

printf "%s\n" "${urls[@]}"

o

(IFS=$'\n'; echo "${urls[*]}")

L'esempio dell'eco sembra strano perché:

  1. viene eseguito in una subshell (le parentesi), quindi non modifico il mio valore attuale di IFS.
  2. L'IFS deve essere definito in un comando separato:
    • Questo non funziona: IFS=$'\n' echo "${urls[*]}"perché la variabile viene espansa prima che la nuova variabile env abbia effetto
    • IFS deve essere impostato prima di iniziare a espandere le variabili.

Inoltre, si noti la sottile differenza nell'indice dell'array di dereferencing utilizzato:

  • [@] nell'esempio printf per espandere l'array in singole parole
  • [*] nell'esempio echo per espandere l'array in una sola parola, con elementi separati dal primo carattere di IFS

È una chiamata difficile, ma sto scegliendo questa risposta perché (1) sembra (AFAIK) il più vicino all'obiettivo dichiarato di sopprimere piuttosto che semplicemente rimuovere gli spazi, e (2) ho imparato di più da esso (a obiettivo dichiarato della mia domanda).
— iconoclasta,

16

Usa printfbuiltin:

$ printf %s\\n localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload}
localhost:8080/reports/promos/130
localhost:8080/reports/promos/130.pdf
localhost:8080/reports/promos/130.xls
localhost:8080/reports/promos/130.xlsx
localhost:8080/reports/promos/130.csv
localhost:8080/reports/promos/130.preload
localhost:8080/reports/promos/130-unburdened
localhost:8080/reports/promos/130-unburdened.pdf
localhost:8080/reports/promos/130-unburdened.xls
localhost:8080/reports/promos/130-unburdened.xlsx
localhost:8080/reports/promos/130-unburdened.csv
localhost:8080/reports/promos/130-unburdened.preload
....

6

Questo è etichettato zsh, quindi suggerisco l'integrato zsh print:

print -l localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload}

-l stampa argomenti su righe separate.


+1 Grazie - buono a sapersi! Lo userò quando sono su zsh. L'ho taggato semplicemente perché uso entrambi e entrambi supportano l'espansione del controvento. (Non so se ce ne sono altri, ma trovo ksh terribilmente confuso, quindi sto lontano.)
— iconoclasta

3

Il problema è che l'espansione del rinforzo sta aggiungendo lo spazio e l'eco sta aggiungendo la nuova riga. Quindi, usando il principio della responsabilità singola, gestisci la nuova riga separatamente.

echo -e localhost:8080/reports/{promos,promo-updates,scandown}/{130,139,142}{,-unburdened,-burdened}{,.pdf,.xls,.xlsx,.csv,.preload} | tr " " "\n"

Penso che questo sia l'approccio più semplice e pratico
— iconoclasta il

No, l'espansione del rinforzo non aggiunge spazio, ma crea diversi argomenti echo. Ecco echoche stampa i suoi argomenti separati da spazi.
— Stéphane Chazelas,

Immagino che il problema si verifichi perché echosepara gli argomenti dagli spazi e la nuova riga viene inserita in aggiunta prima di ogni spazio invece di sostituire lo spazio (che sarebbe più sensato). Dalla memoria, xargsha un problema noto molto simile a questo (specialmente con l' -0opzione)
— syntaxerror
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.