2 Loops gathering input

Greetings all,

I have came up with some code, to read an input file and generate a list, here is a sample of what I am working with. The variable $USER will be inputted by the person running the utility.

 do
 folder=${line%}
 echo "$folder $USER
 done < list.txt

sample of list.txt-

folder1
folder2
folder3

User inputs-

Tom

sample of output of running the loop-

folder1 Tom
folder2 Tom
folder3 Tom

What I want to accomplish, is insted of manually entering a user name, Tom in the example, I want to be able to input a list. Here is the sample output:

List of users-

Tom
Harry
Sally
Joe

Desired Output

folder1 Tom
folder2 Tom
folder3 Tom
folder1 Harry
folder2 Harry
folder3 Harry
folder1 Sally
folder2 Sally
folder3 Sally
folder1 Joe
folder2 Joe
folder3 Joe
                 

What is the best way to approach this. I am thinking two loops but I am still not sure. Help is appreciated. Thanks!

2 loops is the way to go ( a loop within a loop...)

I am not exactly sure how to approach this. what if my list folders has a list of 4, and my list of users has 3.. thats where I got stuck doing the loop within a loop.

Maybe if you shown us what you did so far, and the output, we could help you in understanding what isnt working for you and show you the way to go...

Here is what I am thinking..

do
 folder=${line%}
      user=${line%}
      echo "$folder $user.txt
 done <user.txt
 done < list.txt

that should do it :

for a in $(cat /tmp/folders); do
        for b in $(cat /tmp/users); do
                echo $a" "$b;
        done;
done

Another thing that I came up with-

while read -u 3 -r groups.txt && read -u 4 -r folders.txt; do
		group={$line%}
		folder={$line%}
		  echo  "$folder $user"
done 3<list1..txt 4<list2.txt

How do I make sure that group and folder within the loop point to the right text file?

---------- Post updated at 01:18 PM ---------- Previous update was at 01:06 PM ----------

is giving me-


[jeff@server:/home/jeff/test]> ./for.ksh >> for.out
[jeff@server:/home/jeff/test]> cat for.out
P.P..Pfolders.txtProups.txt P.P..Pfolders.txtProups.txt
[jeff@server:/home/jeff/test]>

Implied double loop - bash 4 needed:

eval printf "%s\\\n" {$(sed -n '1h; 1!H; ${g;s/\n/,/g; p; }' file1)}\" \"{$(sed -n '1h; 1!H; ${g;s/\n/,/g; p; }' file2)}
folder1 Tom
folder1 Harry
folder1 Sally
folder1 Joe
folder2 Tom
folder2 Harry
folder2 Sally
folder2 Joe
folder3 Tom
folder3 Harry
folder3 Sally
folder3 Joe

Beware of the evil eval for the usual, well known reasons...

Still getting the same error. Here is the output I am getting with that:

{P.P..Pfolders.txtProups.txt} {P.P..Pfolders.txtProups.txt}

Here is my script currently, the list of folders is being added to an XML file, and i need to add groups too. take a look (Bold is what I need to add):

		   while read line
			   do
			   folder=${line%}
		       echo "<folder name = \"$folder\" group name = \"$group\">" >> output.xml
			   echo "</folder>" >> output.xml
		    done < folders.txt

This is AIX by the way

---------- Post updated at 02:43 PM ---------- Previous update was at 01:54 PM ----------

I think I may be overthinking this. I divided this into two seperate loops:

while read line
do
group=${line%}
echo "<group=\"$group\">" >> Output.xml
done < groups.txt


while read line
do
group=${line%}
echo "<group=\"$group\">" >> Output.xml
done < groups.txt

My output looks as expected:

<folder name = "Folder3">
</folder>
<folder name = "Folder2">
</folder>
<folder name = "Folder1">
</folder>
<folder name = "Folder0">
</folder>
<file group="TestGroup3">
</file>
<file group="TestGroup2">
</file>
<file group="TestGroup1">
</file>

Now, I need to get each of those 3 groups after the start and end tag of folder..

wouldn't it be easier in awk:

awk 'FNR==NR {f[$0];next} {for (i in f) print i,$0}' folderFile userFile

Yeah, I have played with a few things in awk and sed but I cannot get a viable solution.

where in that snippet that you provided would I place where I want to place the inserted line?

Currently have:

<folder name = "Folder3">
</folder>

Need:

<folder name = "Folder3">
    <file group="TestGroup1">
    </file>
</folder>

Thanks!

how about:

awk -v qq='"' '
   FNR==NR {u[$0];next}
  {
      printf("<folder name = %s%s%s>\n",qq,$0,qq)
      for (i in u) 
         printf("\t<file group =%s%s%s></file>\n",qq,i,qq)
      print "</folder>"
  }' userFile.txt folderFile.txt
1 Like

Looks like that works, help is much appreciated to everyone in this post that helped me!! :b:

$
$ cat folders.txt
Folder3
Folder2
Folder1
$
$ cat groups.txt
TestGroup3
TestGroup2
TestGroup1
$
$ perl -lne '$s ? do{push @g,$_} : do{push @f,$_; $s=1 if eof} }{
             for $i (@f){
                 print "<folder name = \"$i\">";
                 for $j (@g){ print "    <file group = \"$j\"></file>"}
                 print "</folder>"
             }' folders.txt groups.txt
<folder name = "Folder3">
    <file group = "TestGroup3"></file>
    <file group = "TestGroup2"></file>
    <file group = "TestGroup1"></file>
</folder>
<folder name = "Folder2">
    <file group = "TestGroup3"></file>
    <file group = "TestGroup2"></file>
    <file group = "TestGroup1"></file>
</folder>
<folder name = "Folder1">
    <file group = "TestGroup3"></file>
    <file group = "TestGroup2"></file>
    <file group = "TestGroup1"></file>
</folder>
$
$
 

Slower but simpler perhaps, with regular shell scripting:

while read folder
do
  printf '<folder name = "%s">\n' "$folder"
  while read group
  do  
    printf '    <file group = "%s"></file>\n' "$group"
  done < groups.txt
  printf '</folder>\n'
done < folders.txt > Output.xml

suspect some typo on your part.
under regular ksh88 and bash 3 it works:

/tmp$ cat users
Tom
Harry
Sally
Joe
/tmp$ cat folders
folder1
folder2
folder3
/tmp$ cat x.ksh
for a in $(cat /tmp/folders); do
        for b in $(cat /tmp/users); do
                echo $a" "$b;
        done;
done
/tmp$ ./x.ksh
folder1 Tom
folder1 Harry
folder1 Sally
folder1 Joe
folder2 Tom
folder2 Harry
folder2 Sally
folder2 Joe
folder3 Tom
folder3 Harry
folder3 Sally
folder3 Joe