LinuxQuestions.org
Help answer threads with 0 replies.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 07-28-2010, 10:07 AM   #1
Devcon
Member
 
Registered: Nov 2002
Posts: 35

Rep: Reputation: 16
BASH: Download Script -> While Loop Calculation Toubles...


I understand that all while loops in Bash create a subshell when processing piped input. I have a simple download script that displays downloads using DZEN. One of the tests in my script attempts to calculate a free Y-Coordinate to place the window. As multiple instances of the script run simultaneously, I have it dump taken Y-coords to a file. The while loop reads from this file to determine a free coordinate. Enough talk: the code:

Code:
# Determine Y-Coordinate
#########################

COORDS="/tmp/WGET_XY"
CNT=$(ls /tmp/*.wget.* | wc -l)

if [ $CNT -gt 0 ]; then
	while read y; do
	if [ $DZEN_Y -eq $y ]; then
	DZEN_Y=$(( $y - $DZEN_H ))
	else
	echo "$DZEN_Y" >> "$COORDS" && break
	fi
	done < "$COORDS"
else
DZEN_Y=$((738-($CNT*26)))
echo "$DZEN_Y" >> "$COORDS"
fi
DZEN_H in this snippet is just the height of the DZEN instance. I would like the while loop to set the DZEN_Y variable to the highest free Y-coordinate less than 738. I believe the problem is that the DZEN_Y variable is not changed outside the loop; hence, the encompassing if statement eventually returns false and sets DZEN_Y to 712 if multiple instances are running.

I know you guys will have a solution. Thanks.

Last edited by Devcon; 07-28-2010 at 07:24 PM.
 
Old 07-28-2010, 02:00 PM   #2
David the H.
Bash Guru
 
Registered: Jun 2004
Location: Osaka, Japan
Distribution: Arch + Xfce
Posts: 6,852

Rep: Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037Reputation: 2037
That's true, except that you don't have any piped input here, except in the embedded command that sets CNT. A file redirection such as your "< $COORDS" doesn't branch off a subshell.
Code:
#creates a subshell
cat file | while xyz; do
     something
done

#does not create a subshell
while xyz; do
     something
done <file
 
Old 07-28-2010, 03:42 PM   #3
catkin
LQ 5k Club
 
Registered: Dec 2008
Location: Tamil Nadu, India
Distribution: Debian
Posts: 8,578
Blog Entries: 31

Rep: Reputation: 1208Reputation: 1208Reputation: 1208Reputation: 1208Reputation: 1208Reputation: 1208Reputation: 1208Reputation: 1208Reputation: 1208
Is $DZEN_Y initialised when if [ $DZEN_Y -eq $y ]; then is executed? Also -le would be more robust there.
 
Old 07-28-2010, 07:08 PM   #4
Devcon
Member
 
Registered: Nov 2002
Posts: 35

Original Poster
Rep: Reputation: 16
Yes. $DZEN_Y is calculated prior to that test. It defaults based on screen resolution plus a user-defined padding value. The bottom of the stack (first wget instance) is at the bottom right of the screen. Here is the debug output of the 3rd instance of the script (so DZEN_Y should be 686):
Code:
if [[ $CNT -gt 0 ]]; then
	while read y; do
	if [[ $DZEN_Y -eq $y ]]; then
	DZEN_Y=$(( $y - $DZEN_H ))
	else
	echo "$DZEN_Y" >> "$COORDS"  
	break
	fi
	done < "$COORDS"
else
DZEN_Y=$((738-($CNT*26)))
echo "$DZEN_Y" >> "$COORDS"
fi
+ [[ 2 -gt 0 ]]
+ read y
+ [[ 738 -eq 738 ]]
+ DZEN_Y=712
+ read y
I'm not sure why the 738 is properly appended to $COORDS whereas the 712 is not. Thus, all subsequent instances are stacked atop one another at y=712.

Catkin: -le would not work in this case because it would return true even if the y-coord is available. I would like the loop to break if an increment of 26 is found that is less than the values pulled from $COORDS.

Thanks for you input guys.
 
Old 07-28-2010, 07:08 PM   #5
Devcon
Member
 
Registered: Nov 2002
Posts: 35

Original Poster
Rep: Reputation: 16
Heh. Bleh. After looking at it with fresh eyes, the solution presented itself.

Code:
if [[ $CNT -gt 0 ]]; then
        while read y; do
        if [[ $DZEN_Y -eq $y ]]; then
        DZEN_Y=$(( $y - $DZEN_H ))
        else
        break
        fi
        done < "$COORDS"
echo "$DZEN_Y" >> "$COORDS"     # <- This echo statement was the culprit (this is the right position)
else
echo "$DZEN_Y" >> "$COORDS"
fi
I knew it was something stupid. The 712 was not appended because the while loop was going kaplooey before the echo statement was made. I simply had to pull the echo statement out of loop.

Thanks you guys for the suggestions. /SOLVED

Last edited by Devcon; 07-28-2010 at 07:23 PM.
 
Old 07-29-2010, 01:41 AM   #6
grail
LQ Guru
 
Registered: Sep 2009
Location: Perth
Distribution: Manjaro
Posts: 10,006

Rep: Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191Reputation: 3191
Well not to be overly picky but if you do the same thing in the original if and the else you may as well just put it outside.
 
  


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
how to loop over text file lines within bash script for loop? johnpaulodonnell Linux - Newbie 9 07-28-2015 03:49 PM
Making bash script WAIT after starting subshell mintybadger Programming 9 08-04-2011 04:49 AM
Multiple variable for loop (bash) Phier Programming 9 11-24-2009 08:54 AM
Multiple variable for loop (bash) Phier Linux - Newbie 2 11-23-2009 11:13 AM
bash script and exporting variables into a subshell spork Programming 3 10-14-2008 11:38 PM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 10:34 AM.

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