0

I need to generate a file, where each line is a concatenation of a sentence (template) and four variables. Those four variables(their values respectively) have previously been collected in separate lists. So far I have tried:

num = [1,2,3]
fruit = [grape ,banana,pea]
fruits = [grapes, bananas, peas]

with open('result', 'w') as r:
    for n,f,g in num,fruit,fruits: 
        r.writelines("This is string number %d. This is a %s. And I like to eat %s" % (num[n],fruit[f],fruits[g]))

...this approach raises :

TypeError: list indices must be integers, not tuple.

I am also failing at "mungling" this together with different lists, i.e. first concat the first and second variable + string with an intermediate list, to reduce "complexity".

Could someone give me a hint at where i'm failing?

1
  • Thanks everyone for the fast and spot on help! I obviously didn't fully grasp the concept of iteration / its limits. Commented Feb 9, 2014 at 16:42

3 Answers 3

1

A more idiomatic way to solve the problem would be:

template = "This is string number {}. This is a {}. And I like to eat {}\n"
with open('result', 'w') as r:
    for n, f, fs in zip(num, fruit, fruits):
        r.write(template.format(n, f, fs))

Notice the following:

  • In your code, this snippet: in num,fruit,fruits is creating a tuple of three lists; you must use zip() for packing together the input lists and simultaneously traversing them
  • The n,f,g iteration variables in your loop refer to the actual elements in the list, not the indexes. That's why this snippet: num[n],fruit[f],fruits[g] is raising an error
  • The % syntax for formatting strings is deprecated and should be avoided, use format() instead
  • writelines() is for writing a list of lines, for writing a single line at the time use write() passing a \n-terminated string
Sign up to request clarification or add additional context in comments.

1 Comment

Thanks Óscar! The template aproach has been / is novel to me, and raises a KeyError, for the second substitution. But I will definitely look up the docs, esp since it's supposed to become the new standard
1

For statement in python has the following syntax.

for <value> in <iterable>:
   body 

List is a <iterable> data type. 

For now, it means you can traverse it. I would recommend you read documentation for more informatino about iterables and how to implement them in your classes definitions.

but list,list,list is not. you will need to concatenate these lists into one list.

zip(l1,l2,l3) would do it for you as a pattern match. it would make a list with elements matching with index in a tuple.

you can unmatch it at value

in your case

for (n,f,g) in zip(num,fruit,fruits): 

will do.

Comments

0

num,fruit,fruits gives a tuple, which makes for n,f,g in num,fruit,fruits: equals:

atuple=num,fruit,fruits
for n,f,g in atuple:
    ...

so the for-loop unpack atuple[0] (namely, num) , assign values num[0], num[1], num[2] to n,f,g, and then fruit[0], fruit[1], fruit[2]... that's why you get the error.

Change for n,f,g in num,fruit,fruits: to :

for tup in zip(num,fruit,fruits): 
    r.writelines("This is string number %d. 
                  This is a %s. And I like to eat %s" % tup)

see docs for zip

2 Comments

The user is new to python and needs his mistake explained, not fixed.
Thanks Zhang! Copied your solution, works like a charm.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.