Reputation: 1482
I'm trying to learn the python scripting . Being some body who started coding in c/c++ or java i'm finding it extremely hard to find ways to write loops in python , especially for loops with conditions
I've a list A of string, i need to do a specific op on these strings a pair at a time ,say xor of the strings Also xor(a,b)=xor(b,a), hence i need to remove the redundant pair while looping
In traditional lang i would do something like
for(i=0;i<len;i++){
for(j=i+1;j<len;j++){
res[count]=xor(a[i],a[j])
count++;
}
}
So how do I implement the same with Python, I could think of iterators but is there a more efficient way , something very obvious eluding my eyes???
Upvotes: 0
Views: 1016
Reputation: 11
It is quite easy,
Nested loops means there are multiple loops. Always remember that outer loop control the repeatation of inner loop.
for letter in [ 'a', 'b'] :
for num in [1,2,3]:
print(letter, num)
Output will be like - a1, a2, a3, b1, b2, b3
You can see that each element of outer loop engages with each element of inner loop. Thats what nested loop does.
Upvotes: 1
Reputation: 1117
This nested Python loop should solve your problem.
for i in range(len(a)):
for j in range(i+1,len(a)):
#do stuff
Upvotes: 0
Reputation: 11122
Here is another translation:
res = []
for i in range( len( a ) ):
for j in range( i + 1 ):
res.append( a[i] ^ a[j] )
or even this one liner
res = [ a[i] ^ a[j] for i in range( len( a ) ) for j in range( i ) ]
Upvotes: 1
Reputation: 110696
As you can see - there are plenty ways of doing it - using functions in the itertools module or rewritng then as lit comprehensions. Those, however, although nice, reduce readbility over conscision, and since you are starting now in Python, one important thing is to learn to think in "for" loops the Python way.
And the Python way fo for loops is: You don't iterate over indexes - you have sequences, and you want to perform actions for each element on a sequence - in C (and its derivatives) one does that indirectly by calculating the string length, iterating numbeers from 0 to the string lenght, an dusing those numbers as indexes on the string. In Python, the string is a sequence - you just use it as the element you want to interact on.
Apart from for loops, in Python, string items are substrings of len(1), not numbers on the 0-255 range, so you have to explicitly convert those to integers, perform the xor operation, and back - this canbe written as a one line lambda function such as :
xor = lambda c1, c2: chr(ord(c1) ^ ord(c2))
Alternatively, you can use "bytearray" objects that mimic strign, but behave somewhat like c strigns in a sense they are mutable, and its elements are treated as numbers in the 0-255 range.
As for your code:
res = ""
for position, char1 in enumerate(a):
for char2 in a[position + 1:]:
res += xor(char1, char2)
The "enumerate" call gives one the position of the element we are interating along with the element itself for cases like this.
Upvotes: 1
Reputation: 215039
Python comes with batteries included, that is, most of the stuff like this is already written for you. If you want combinations of strings, there is a dedicated function for that:
import itertools
result = []
for pair in itertools.combinations(a, 2):
result.append(xor(pair[0], pair[1]))
or simply:
result = [xor(*p) for p in itertools.combinations(a, 2)]
Upvotes: 3
Reputation: 43064
In python you often don't need loops like that because Python has implied loops as part of sequence operators such as slicing and list comprehensions. Also, you should not mutate a list while iterating over it so you just create a new list.
def xor(s1, s2):
return "".join([chr(ord(a)^ord(b)) for a,b in zip(s1, s2)])
a = ["ab", "ba", "ab", "ba", "ab", "ba", "ab", "ba", "ab", "ba", "ab", "ba"]
res = [xor(a,b) for a,b in zip(a[::2], a[1::2])]
print(repr(res))
Upvotes: 0