LinuxQuestions.org
Share your knowledge at the LQ Wiki.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Linux Forums > Linux - Newbie
User Name
Password
Linux - Newbie This Linux forum is for members that are new to Linux.
Just starting out and have a question? If it is not in the man pages or the how-to's this is the place!

Notices


Reply
  Search this Thread
Old 12-26-2006, 12:15 PM   #1
Haloony
Member
 
Registered: Aug 2005
Posts: 61

Rep: Reputation: 15
For Loop Help


Hey guys I am having some trouble operating the for loop. I am trying to change permission rights on every file in a folder. I want to change the ownerships from root to another user. I know there are probably much easier ways to do this, but I really won't stop until i get it to work. here is my code:
Code:
hal@Hal-Laptop:~$ for x in  $ls /home/hal/comics/Amazing_Spiderman_1-535/; do chown hal $x; done 
hal@Hal-Laptop:~$
According to the results I got from the terminal, my for loop worked, but when I checked the files, the ownerships had not changed. So i tried entering something slightly different into the terminal and this is what happened:
Code:
hal@Hal-Laptop:~$ for x in `$ls /home/hal/comics/Amazing_Spiderman_1-535/`; do chown hal $x; done
bash:/home/hal/comics/Amazing_Spiderman_1-535/: is a directory
hal@Hal-Laptop:~$
I am not sure what I am doing wrong so any guidance would be appreciated. Thanks, Hal
 
Old 12-26-2006, 12:28 PM   #2
Nylex
LQ Addict
 
Registered: Jul 2003
Location: London, UK
Distribution: Slackware
Posts: 7,464

Rep: Reputation: Disabled
It should be "for x in $(ls /home/hal/comics...) ..." or "for x in `ls /home/hal/comics...` ...", because you either use $ or the backticks for command substitution, not both.
 
Old 12-26-2006, 03:37 PM   #3
kaz2100
Senior Member
 
Registered: Apr 2005
Location: Penguin land, with apple, no gates
Distribution: SlackWare > Debian testing woody(32) sarge etch lenny squeeze(+64) wheezy .. bullseye bookworm
Posts: 1,832

Rep: Reputation: 108Reputation: 108
Hi,

Next time, before you ask,
add
Code:
#!/bin/sh -x
and examine output.

Happy Penguins!
 
Old 12-26-2006, 03:45 PM   #4
Haloony
Member
 
Registered: Aug 2005
Posts: 61

Original Poster
Rep: Reputation: 15
Hey Nylex,
Thanks for the reply, your solution corrected my syntax error. Now I have another, but slightly unrelated question. I said before that I was trying to change ownerships on all the files in a directory, but these files were moved from a windows partition. The problem is that these filenames have spaces in them, and the chown command reads the words of the filenames, as files themselves, because of the spaces between them. I was wondering if there is something I can do to fix the filenames, without having to do them one by one. Usually a for loop would be helpful to rename many files, but the mv command, like chown, would not be able to read the filenames as they really are. Thanks for the help, Hal.
 
Old 12-26-2006, 04:35 PM   #5
pwc101
Senior Member
 
Registered: Oct 2005
Location: UK
Distribution: Slackware
Posts: 1,847

Rep: Reputation: 128Reputation: 128
To replace spaces with underscores:
Code:
#! /bin/sh
for i in *
do mv "$i" "$(echo ${i// /_})"
done
save it as a script and run from the current directory. If you wanted to reverse the process, just change
Code:
${i// /_}
to
Code:
${i//_/ }
Incidentally, to change all the ownerships of files within a directory, this would also work:
Code:
chown user:group *
where user is the user you want to change the ownership to, and group is the group

Last edited by pwc101; 12-26-2006 at 04:37 PM.
 
Old 12-26-2006, 07:15 PM   #6
Haloony
Member
 
Registered: Aug 2005
Posts: 61

Original Poster
Rep: Reputation: 15
Hey pwc101,
The script you gave me worked perfectly and I wanted to thank you for that. I was able to change file permissions the way I wanted to, so everything worked out fine. Although the script did work, I want to understand why it does. Im confused about the second part of the "do" clause:
Code:
"$(echo ${i// /_})"
I am not sure I understand how it operates to alter the filename, on account of spaces and underscores. So it would be great if you or someone could explain the logic to the script. Thanks again, Hal.
 
Old 12-27-2006, 08:18 AM   #7
pwc101
Senior Member
 
Registered: Oct 2005
Location: UK
Distribution: Slackware
Posts: 1,847

Rep: Reputation: 128Reputation: 128
It's variable expansion, and is quite nicely summarised in this post:

http://www.linuxquestions.org/questi...85#post2333585
 
Old 12-27-2006, 11:16 AM   #8
wmakowski
Member
 
Registered: Oct 2003
Location: Ohio
Distribution: Fedora 25, 26, RHL 5.2
Posts: 560

Rep: Reputation: 56
Another name for it is Parameter Expansion. There is a section on this in the bash man page too. Several other methods of manipulating parameters are listed.

Bill
 
Old 12-28-2006, 10:11 AM   #9
Haloony
Member
 
Registered: Aug 2005
Posts: 61

Original Poster
Rep: Reputation: 15
I understand the concept of command substitution in general, but I don't understand the logic behind the forward slashes. When I was learning how command substitution operated, I only came across backslashes and their function in escaping, but I don't understand the function of forward slashes or the double slash.Thanks, Hal
 
Old 12-28-2006, 10:24 AM   #10
pwc101
Senior Member
 
Registered: Oct 2005
Location: UK
Distribution: Slackware
Posts: 1,847

Rep: Reputation: 128Reputation: 128
${parameter//pattern/string}
The pattern is expanded to produce a pattern just as in filename expansion. Parameter is expanded and the longest match of pattern against its value is replaced with string. In the first form, only the first match is replaced. The second form causes all matches of pattern to be replaced with string. (from http://www.linuxtopia.org/online_boo...shref_29.html).

So basically, the double forward-slash causes all occurrences of pattern to be replaced with string. In our case, that's " " with "_", so ${i//this/that} would find all occurrences of "this" within our original variable $i (which is a filename), and substitute them with "that". I think.

edit: ${i/this/that} would only do the first occurrence of "this", not all occurrences.

Last edited by pwc101; 12-28-2006 at 10:26 AM.
 
  


Reply



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
bc in for loop twantrd Programming 2 05-17-2006 06:47 PM
If, else, then or loop, help. ncsuapex Programming 10 02-24-2006 03:07 PM
for loop only works properly on first loop symo0009 Programming 1 12-25-2005 05:17 PM
WHILE LOOP in 'C' ']['HeBroken Programming 4 10-29-2004 01:42 AM
for loop klfreese Programming 16 08-11-2003 11:09 AM

LinuxQuestions.org > Forums > Linux Forums > Linux - Newbie

All times are GMT -5. The time now is 05:03 PM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration