Forum |  HardWare.fr | News | Articles | PC | S'identifier | S'inscrire | Shop Recherche
1007 connectés 

  FORUM HardWare.fr
  Programmation
  Shell/Batch

  [SHELL] Renommer les noms de fichiers avec espaces

 


 Mot :   Pseudo :  
 
Bas de page
Auteur Sujet :

[SHELL] Renommer les noms de fichiers avec espaces

n°1970854
Kerrozen
To be or not to be ... cool ..
Posté le 03-03-2010 à 14:18:06  profilanswer
 

Contexte : KSH  
 
Question récurrente, rébarbative et sans doute revisitée souvent mais.... (y a toujours un 'mais' bien marrant  :na: )
 
Pas de souci pour modifier l'affichage des noms de mes fichiers, un truc tout con genre ce qui suit suffit :

Code :
  1. ls | sed 's/  */_/g'


 
Seulement Quid quand il s'agit de renommer ces fichiers ? car là, quand on fait une boucle avec un ls ou un find, le paramètre itératif de la boucle contient systématiquement une découpe en fonction des espaces, et du coup c'est la mouïse !
 
Explication par l'exemple :
 

Code :
  1. for fic in $( ls )
  2. do
  3.    mv "$fic" `echo $fic | sed 's/  */_/g'`
  4. done


 
Ben là ça fonctionne plus du tout, car le ls lui, il vous découpe tout avec les espaces....  :kaola:  :fou:  :o  :non:  
 
J'avoue je cale en peu aujourd'hui, les neurones semblent fatigués.
 
Merci d'avance pour l'éventuel coup de main


Message édité par Kerrozen le 03-03-2010 à 14:18:29

---------------
En programmation, quand t'as un problème et qu'il n'y a que deux solutions valides, seule la troisième fonctionne !
mood
Publicité
Posté le 03-03-2010 à 14:18:06  profilanswer
 

n°1970857
Kerrozen
To be or not to be ... cool ..
Posté le 03-03-2010 à 14:31:05  profilanswer
 

Bon, finalement les neurones se sont réveillés grâce à Google qui est mon ami.
 
La commande magique est la suivante :
 

Code :
  1. for i in *
  2. do
  3.        mv "$i" `echo "$i" | sed 's/  */_/g'`
  4. done


 :love:  :love:  :love:  
 
Ce qui est vraiment bébête, je le reconnais   :jap:  
 
En revanche, comprendre pourquoi quand on utilise un ls ça fonctionne pas et pourquoi donc ça fonctionne avec *  ...... alors là....... Si un gourou local pouvait me faire un petit topo, mes neurones et moi même serions tout à fait comblés !
 
Merci quand même ! (ben oui, le fait d'écrire ici donne l'impression qu'on doit tout faire pour trouver une réponse avant les autres ^^ c'est motivant !)


---------------
En programmation, quand t'as un problème et qu'il n'y a que deux solutions valides, seule la troisième fonctionne !
n°1970878
olivthill
Posté le 03-03-2010 à 15:22:45  profilanswer
 

Beaucoup de monde utilise for sans se méfier que cela coupe les variable là où se trouve une fin de ligne ou un espace. Je ne sais pas pourquoi for in * marche. En tous cas, j'utilise read qui marche sans problème.
 
Voici un script de test :

echo "=== 1. for i in dollar( ls ) ==="
for i in $( ls )
do
   echo $i
done
 
echo "=== 2. ls | while read i ==="
ls | while read i
do
   echo $i
done
 
echo "=== 3. for i in * ==="
for i in *
do
   echo $i
done

Dans mon répertoire, j'ai

fichier un.txt
fichier_deux.txt
test1.sh

Le résultat est :

=== 1. for i in dollar( ls ) ===
fichier
un.txt
fichier_deux.txt
test1.sh
=== 2. ls | while read i ===
fichier un.txt
fichier_deux.txt
test1.sh
=== 3. for i in * ===
fichier un.txt
fichier_deux.txt
test1.sh


n°1976222
Kerrozen
To be or not to be ... cool ..
Posté le 23-03-2010 à 10:54:16  profilanswer
 

En ce qui concerne le read, je suis moins étonné : il va de lui même stocker toute la ligne qu'il lit avec ses espaces et autres tabulations (donc ce que tu lui envoie via le pipe ) directement dans une variable. Là donc pas de problème. J'aurai d'ailleurs effectivement pu réagir tout de suite en l'utilisant plutôt que d'insister avec mon FOR : bien vu !
 
Mais quand même, j'avais bien compris la méthode de découpe du for : espaces, sauts de lignes, tabulations etc etc... et c'est bien pour ça que je suis assez interloqué par le comprtement avec "*" ?
 
Personne ne saurait nous donner le détail avancé de ce qui se passe ?


---------------
En programmation, quand t'as un problème et qu'il n'y a que deux solutions valides, seule la troisième fonctionne !
n°1978010
Sve@r
Posté le 27-03-2010 à 17:37:00  profilanswer
 

Kerrozen a écrit :

Mais quand même, j'avais bien compris la méthode de découpe du for : espaces, sauts de lignes, tabulations etc etc... et c'est bien pour ça que je suis assez interloqué par le comprtement avec "*" ?
 
Personne ne saurait nous donner le détail avancé de ce qui se passe ?


 
C'est parce que l'étoile est transformée par le programme chargé de lire le clavier et transmettre ensuite l'ordre lu au shell.
Et ce logiciel encadre alors tout fichier avec espace par deux quottes simples '     '
 
Suffit d'activer le débuggueur shell "set -x" et de taper ensuite "echo *". Le débuggueur montrera la vraie commande reçue et on voit les noms avec espace encadré de ces quottes.
 
Partant de là, si le répertoire contient un fichier "a a", on comprend pourquoi un for i in * ne découpe pas le nom "a a" car le shell aura reçu 'a a' (un seul token bien protégé) alors que for i in `ls` lui fait recevoir a a (2 tokens apparemment non liés)


---------------
Vous ne pouvez pas apporter la prospérité au pauvre en la retirant au riche.
n°1978044
Elmoricq
Modérateur
Posté le 27-03-2010 à 21:03:30  profilanswer
 

olivthill a écrit :

Je ne sais pas pourquoi for in * marche.


 
Le shell échappe les caractères spéciaux. :)

n°1978764
Kerrozen
To be or not to be ... cool ..
Posté le 30-03-2010 à 10:22:06  profilanswer
 

Sve@r a écrit :


 
C'est parce que l'étoile est transformée par le programme chargé de lire le clavier et transmettre ensuite l'ordre lu au shell.
Et ce logiciel encadre alors tout fichier avec espace par deux quottes simples '     '
 
Suffit d'activer le débuggueur shell "set -x" et de taper ensuite "echo *". Le débuggueur montrera la vraie commande reçue et on voit les noms avec espace encadré de ces quottes.
 
Partant de là, si le répertoire contient un fichier "a a", on comprend pourquoi un for i in * ne découpe pas le nom "a a" car le shell aura reçu 'a a' (un seul token bien protégé) alors que for i in `ls` lui fait recevoir a a (2 tokens apparemment non liés)


 
 :bounce:  :jap:  :jap:  :jap:  :jap:  :jap:  :bounce:  
 
J'savais bien que j'aurai la réponse en venant causer ici ! Merci beaucoup à Sve@r !
On en apprend tous les jours.


---------------
En programmation, quand t'as un problème et qu'il n'y a que deux solutions valides, seule la troisième fonctionne !

Aller à :
Ajouter une réponse
  FORUM HardWare.fr
  Programmation
  Shell/Batch

  [SHELL] Renommer les noms de fichiers avec espaces

 

Sujets relatifs
Fichiers a rendre public ou prive sur site web genre .htaccessSysteme de cache et nombre de fichiers
lier deux fichiers excelCréer un programme de génération de fichiers son
fichiers .vcproj et .sln[C/C++] Transformation de fichiers
[Batch] Transformation des fichiers[Thread?] Liste de fichiers
[Shell/sh] Parcours recursif de répertoire et création de liens[SHELL] Connexion base DB2 + lancement requête dans fichier .sql
Plus de sujets relatifs à : [SHELL] Renommer les noms de fichiers avec espaces


Copyright © 1997-2022 Hardware.fr SARL (Signaler un contenu illicite / Données personnelles) / Groupe LDLC / Shop HFR