Take the 2-minute tour ×
Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

I define a list in bash like this:

list="element1 element_2 my_element_3 element04"

and I want to do a loop where I iterate through all possible pair combinations. In Perl, I would use a while/foreach with a shift on the list like this:

while (my $element1 = shift (@list)) {
  foreach my $element2 (@list) {
      print "$element1 - $element2\n";
  }
}

I don't want the same element in the pair and don't care about the order of the pairs, so if the list is "A B C", the result should be:

A - B
A - C
B - C

How can I do the equivalent in bash?

share|improve this question
add comment

3 Answers

up vote 5 down vote accepted

The simplest approach seems to be to use positional parameters.

set -- value1 value2 "value with spaces"
for a; do
    shift
    for b; do
        printf "%s - %s\n" "$a" "$b"
    done
done
share|improve this answer
    
hmmmm, just to clarify, I don't want the same element in the pair and don't care about the order of the pairs, I've edited my question now. –  130490868091234 Aug 2 '11 at 13:12
    
I just saw the shift in your original question as well. Updated answer to match. –  jw013 Aug 2 '11 at 13:21
add comment

dump the output to standard out, pipe to sort -u

share|improve this answer
add comment

Another way to think about your problem is: if you had (i,j) indexes for each item in your list, you would only be interested in the set of items above (or below) the diagonal (ie, where i>j).

If you did want all combinations, then you only have to test where i!=j.

I wanted to do a similar thing: generate all possible orderings of 4 items. For loops nested to a depth of 4 would not be very pretty, and an elegant conditional didn't come to mind, but this solution did:

$ for combo in  {en,fa,sp,ru}{en,fa,sp,ru}{en,fa,sp,ru}{en,fa,sp,ru}; do echo $combo; done | egrep -v 'en.*en|fa.*fa|sp.*sp|ru.*ru' 
enfaspru
enfarusp
enspfaru
ensprufa
enrufasp
enruspfa
faenspru
faenrusp
faspenru
faspruen
faruensp
faruspen
spenfaru
spenrufa
spfaenru
spfaruen
spruenfa
sprufaen
ruenfasp
ruenspfa
rufaensp
rufaspen
ruspenfa
ruspfaen
share|improve this answer
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.