J'ai lu d'autres questions sur la manipulation de chaînes bash de piping mais elles semblent être des applications spécialisées.
Essentiellement, existe-t-il un moyen de faire le plus simple ci-dessous?
au lieu de
$ string='hello world'; string2="${string// /_}"; echo "${string2^^}"
HELLO_WORLD
quelque chose comme
$ echo 'hello world' | $"{-// /_}" | "${ -^^}"
HELLO_WORLD
Edit Je suis intéressé à rester dans les manipulations bash si possible pour maintenir la vitesse (par opposition à sed / awk qui ont tendance à ralentir considérablement mes scripts)
Edit2: @jimmij
J'aime le deuxième exemple et m'a amené à faire une fonction.
bash_m() { { read x; echo "${x// /_}"; } | { read x; echo "${x^^}"; }; }
echo hello world | bash_m
HELLO_WORLD
tr
manuel, alors l'inverse est vrai parce que le temps d'apparition des processus est négligeable par rapport au temps de manipulation de chaîne pour lequelsed
etawk
sont dédiés. Si la chaîne est extrêmement longue, disons tout le manuel de bash, alors bash peut simplement refuser de continuer, en raison de certaines limitations internes.sed
,awk
,tr
ou similaires. Regardez la réponse de gena2x, que j'ai modifiée il y a quelque temps en ajoutant exactement ces informations: unix.stackexchange.com/questions/162221/… vous voudrez peut-être la comparer avec la réponse de terdon à la même question où il donne du temps pour les chaînes courtes dans lesquelles le processus de traitement des cas prend le plus de temps. Vous pouvez le tester vous-même et publier le résultat.read x; echo $x
est meilleur pour la performance? La syntaxe ne semble ni plus courte ni plus propre.x=${x// /_}; x=${x^^}
est une manière beaucoup plus concise de faire la même chose que{read x; echo ${x...
. En ce qui concerne les performances, @jimmij a souligné quetr
/sed
serait plus rapide quebash
, le nombre de fourches étant égal. L'utilisation d'un tuyau entraîne toujours un processus supplémentaire, donc l'argument de l'enregistrement d'une fourche ne s'applique plus. Ainsi, si vous utilisez des pipes, utilisez simplementsed
/tr
etc. Si vous pouvez le faire en bash, faites-le et sautez ceread x; echo $x
non - sens.Réponses:
Ce que jimmij a dit. Son dernier exemple est le plus proche que vous pouvez obtenir de ce que vous tentez dans votre expression canalisée.
Voici une variante sur ce thème:
Je serais enclin à l'utiliser
tr
, car c'est assez rapide.Je suppose que c'est dommage que bash ne permette pas l'expansion de paramètres imbriqués; OTOH, l'utilisation de telles expressions imbriquées pourrait facilement conduire à un code difficile à lire. À moins que vous ayez vraiment besoin que les choses tournent le plus vite possible, il vaut mieux écrire du code facile à lire, à comprendre et à maintenir, plutôt que du code intelligent qui est un PITA à déboguer. Et si vous avez vraiment faire les choses doivent être faites à toute vitesse , vous devez utiliser le code compilé, pas un script.
la source
Vous ne pouvez pas transmettre des extensions de paramètres de cette manière. Lorsque vous vous référez à l'
x
utilisation du$
symbole comme dans le"${x}"
formulaire, il doit s'agir d'un vrai nom de variable, pas d'une entrée standard, du moins pas dansbash
. Dans,zsh
vous pouvez effectuer des substitutions de paramètres imbriqués de la manière suivante:(note:
:u
est pourzsh
le même que^^
pourbash
)L'imbrication dans bash n'est pas possible et je pense que ce que vous avez écrit en question est le meilleur que vous puissiez obtenir, mais si pour une raison étrange vous devez impliquer des tuyaux dans l'équation, vous pouvez essayer ceci:
la source
tr
/sed
sont plus rapides qu'aubash
traitement des chaînes et sur la façon dont vous utilisez les canaux pour passer les chaînes via les E / S standard, je vois littéralement zéro point de faire ces opérations en bash par opposition àtr
/sed
. Pourquoi serait-on jamais| { read x; echo $x... }
opposé à un| sed
qui fait la même chose?echo
etread
sont bash intégrés, donc en principe un peu plus rapide). Comme je l'ai déjà écrit dans la réponse, les manipulations progressives des paramètres que OP a dans la question est la meilleure que l'on puisse obtenir à mon avis pour cette tâche en bash. Quoi qu'il en soit, le problème est plutôt académique.