run commands in parallel

For discussions about programming, programming questions/advice, and projects that don't really have anything to do with Puppy.
Post Reply
Message
Author
User avatar
Lobster
Official Crustacean
Posts: 15522
Joined: Wed 04 May 2005, 06:06
Location: Paradox Realm
Contact:

run commands in parallel

#1 Post by Lobster »

In this prog, the music plays then when it stops
the image is displayed
How to run at the same time?

Code: Select all

#! /bin/bash
madplay ivy.mp3 "$@"
xcowsay --cow=Lobster6 --time=1 --dream=puppylogo96.png "$@"
Sure I have asked this before - can not find reply
Last edited by Lobster on Sun 27 Jun 2010, 04:51, edited 1 time in total.
Puppy Raspup 8.2Final 8)
Puppy Links Page http://www.smokey01.com/bruceb/puppy.html :D

ken geometrics
Posts: 76
Joined: Fri 23 Jan 2009, 14:59
Location: California

Re: run commnds in parallel

#2 Post by ken geometrics »

Lobster wrote:In this prog, the music plays then when it stops
the image is displayed
How to run at the same time?

Code: Select all

#! /bin/bash
madplay ivy.mp3 "$@"
xcowsay --cow=Lobster6 --time=1 --dream=puppylogo96.png "$@"
Sure I have asked this before - can not find reply
Many things will run in multiple tasks if you put the "&" on the end of the line.

Try:

Code: Select all

madplay ivy.mp3 "$@" &
xcowsay --cow=Lobster6 --time=1 --dream=puppylogo96.png "$@" &

echo "And this too"

User avatar
Lobster
Official Crustacean
Posts: 15522
Joined: Wed 04 May 2005, 06:06
Location: Paradox Realm
Contact:

#3 Post by Lobster »

Thanks ken geometrics,

I will just put on my dunce hat
and go stand in the corner . . . :oops:
Puppy Raspup 8.2Final 8)
Puppy Links Page http://www.smokey01.com/bruceb/puppy.html :D

User avatar
Pizzasgood
Posts: 6183
Joined: Wed 04 May 2005, 20:28
Location: Knoxville, TN, USA

#4 Post by Pizzasgood »

As mentioned, sticking an ampersand on the end of a command will background it, so that it runs in parallel. However, what if you have a group of commands that should execute sequentially, but you want the group to run in parallel to the rest of the script? Well, you could put it into a function and run the function in parallel. Another option is to put it into a subshell by wrapping it in parenthesis, and then stick an ampersand after the closing paren.

The following is an example of that. It has a block of code at the top that will run in parallel to the rest of the code. That first part just opens four terminals.

The second part of the code, which will run at the same time as the first part (indeed, it will probably finish first), draws a picture in your terminal. For best results, use a terminal with a black background. With most terminals, that can be achieved by running them with the the -bg black -fg white options.

I got a bit carried away on that second part 8)

Code: Select all

#!/bin/sh
#This opens several terminals, one per second.  At the same time, a
#Different set of code gradually draws an image on the screen.

#Create the files
(
        #try to find a terminal
        for i in xterm rxvt urxvt sakura; do
                which $i >/dev/null && terminal=$i
        done
        for i in {0..3}; do
                urxvt &
                sleep 1
        done
) &

########################################################################

#This part does the drawing of cool things.
#Note:  If you want to use this independently of this example, just cut
#everything below the following line.  All the above is irrelevant.
###--------- CUT AFTER THIS --------------------------------------------
#!/bin/sh
#Draws a pretty picture

#This looks best in a terminal with a black background.  For example:
#    rxvt -bg black -fg white

h=12
tw=4 #even for alignment
th=3
#increasing this dehances the chrome factor
scarcity=9

###################################################
#define a bunch of colors
#the capitalized versions are "bold" or "bright"

 black='\033[0;30m'
 BLACK='\033[1;30m'
 white='\033[0;37m'
 WHITE='\033[1;37m'

   red='\033[0;31m'
   RED='\033[1;31m'
 green='\033[0;32m'
 GREEN='\033[1;32m'
yellow='\033[0;33m'
YELLOW='\033[1;33m'
  blue='\033[0;34m'
  BLUE='\033[1;34m'
purple='\033[0;35m'
PURPLE='\033[1;35m'
  cyan='\033[0;36m'
  CYAN='\033[1;36m'

    NC='\033[0m'
  grey=$BLACK
###################################################

char1="${green}/${NC}"
char2="${green}^${NC}"
char3="${green}\\\\${NC}"
chart1="${yellow}|${NC}"
chart2="${yellow}=${NC}"
chart3="${yellow}|${NC}"

function draw_bulb(){
        char="*"
        color_pool=($RED $YELLOW $BLUE $CYAN $PURPLE)
        let "index=RANDOM%${#color_pool[@]}"
        echo "${color_pool[$index]}${char}${NC}"
}

function draw_item(){
        boring="$1"
        let 'decision=RANDOM%scarcity'
        if [ $decision -eq 0 ]; then
                draw_bulb
        else
                echo "$boring"
        fi
}

let 'w=h*2'

let 'cx=w/2'
let 'cy=h/2'

for x in $(seq 0 $cx); do
        line_start="${line_start} "
done
echo -e "${line_start}${WHITE} _A_ ${NC}"
echo -e "${line_start}${WHITE} /^\ ${NC}"

for y in $(seq 1 $h); do
        let 'x1=cx-y+1'
        let 'x2=cx+y-1'
        line=''
        for x in $(seq 0 $x1); do
                line="${line} "
        done
        line="${line} $(draw_item "$char1")"
        let 'start=x1+1'
        let 'end=x2-1'
        for x in $(seq $start 2 $end); do
                line="${line} $(draw_item "$char2")"
                #line="${line} ${char2}"
        done
        line="${line} $(draw_item "$char3")"
        echo -e "$line"
        let 'y++'
done
for y in $(seq 1 $th); do
        let 'x1=cx-tw/2'
        line=''
        for x in $(seq 0 $x1); do
                line="${line} "
        done
        line="${line} ${chart1}"
        let 'start=x1+1'
        let 'end=x1+tw'
        for x in $(seq $start 2 $end); do
                line="${line} ${chart2}"
        done
        line="${line} ${chart3}"
        echo -e "$line"
done
[size=75]Between depriving a man of one hour from his life and depriving him of his life there exists only a difference of degree. --Muad'Dib[/size]
[img]http://www.browserloadofcoolness.com/sig.png[/img]

User avatar
Iguleder
Posts: 2026
Joined: Tue 11 Aug 2009, 09:36
Location: Israel, somewhere in the beautiful desert
Contact:

#5 Post by Iguleder »

There's another method, in plain C. It was originally written for my own distro to speed up init so it starts things in parallel ... works great :)

Code: Select all

//dr 0.1 by Iguleder

// To compile:
// gcc -lpthread -o dr dr.c

#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>

void *runThread(void *command)
{

  system(command);

}

int main(int argc, char** argv) {
    
  pthread_t commandThreads[argc-1];
  long i;

  for(i=1; i<=argc-1; i++)
  {

    pthread_create(&commandThreads[i-1], NULL, runThread, (void *)argv[i]);
      
  }

  pthread_exit(NULL);

}
To use it: compile, put in /usr/bin, then do "dr <command 1> <command 2> <command 3> [ ... ]".

In your case:
dr "madplay ivy.mp3 $@" "xcowsay --cow=Lobster6 --time=1 --dream=puppylogo96.png $@"
[url=http://dimakrasner.com/]My homepage[/url]
[url=https://github.com/dimkr]My GitHub profile[/url]

potong
Posts: 88
Joined: Fri 06 Mar 2009, 04:01

#6 Post by potong »

Xargs has a -P n option which will run maximum number of n jobs at a time or use -P 0 to run all ( I don't think this option is available on BusyBox).

GNU parallel is more fancy and can do all manner of clever things on single/multiple processor machine(s) see here for a screen cast
and here for the home page

HTH

Potong

Post Reply