Python - Sum doesn't work in list comprehension syntax if source is file

I am new to Python and I am studying list comprehension.

What I'm trying to do is convert the following code into a list comprehension:

def words_without_e(): count = 0 words = open('words.txt') for word in words: if word.find('e') == -1: count += 1 words.close() return count 

Here is my weak attempt:

 words = open('words.txt') print sum([1 for word in words if word.find('e') == -1]) 

But, unfortunately, it does not work. The answer I expect to get is 37641, but I get 0. :(

I tried to create another code doing the same thing, but instead of the file as the source, I used a list:

 def test(): words = ['hello', 'world', 'ciao'] return sum([1 for word in words if word.find('e') == -1]) 

And it works.

I saw this "pretty" analogous SO article and tried to post return len([word for word in words if len(word) >= 2 and word[0] == word[-1]]) code there. It works if the source is a hard-coded list, but fails if the source is an external file.

Now, my question is: does sum only work with lists and tuples? If I understand the docs , you can list any iterative data.

Any enlightenment would be greatly appreciated. :)

+2
source share
3 answers

The simplest solution is the following:

 with open("words.txt") as words: sum(1 for word in words if "e" not in word) 

As you can see, sum works with any iterator - here I use a generator expression.

Instead of doing word.find('e') == -1 , we can just make "e" not in word , which is better to read and work, because the lines themselves are repeated and support __contains__ .

I also use the with statement to open files - it is preferable to manually open and close them, since it handles these things for you and correctly processes exceptions.

I would like to point out, however, your example works for me. I assume that your file is a space or a comma, but a loop through the file returns strings.

My test file:

 bob bill james test something no 

This, for example, will not work:

 bob bill james test something no 

How do we get one line containing all this. In this case, we can use str.split() to split the lines into words.

eg:

 with open("words.txt") as lines: sum(1 for line in lines for word in line.split() if "e" not in word) 
+7
source

I just tried this and it works, so it may have something to do with how your file is formatted:

 me@pc :~/Desktop$ cat > words.txt app noot mies wim zus jet me@ps :~/Desktop$ python Python 2.6.6 (r266:84292, Dec 26 2010, 22:31:48) [GCC 4.4.5] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> sum(1 for word in open('words.txt') if 'e' not in word) 4 
+1
source

Good. I tried the code @Lattyware wrote and it works great. I think I already found the culprit, although I don’t understand why he behaves this way. I think it will be on a different issue. :)

 def count_words(): with open("words.txt") as words: print sum(1 for word in words) print sum(1 for word in words if "e" not in word) >>> count_words() 113809 0 

But when I commented on the first print statement, it correctly displays the answer.

 >>> count_words() 37641 

UPDATE:

I am posting the solution that I came up with in case anyone else runs into the same problem.

 def count_words(): total = 0 wordsWithoutE = 0 with open("words.txt") as words: for word in words: if 'e' not in word: wordsWithoutE += 1 total += 1 return (total, wordsWithoutE) >>> print count_words() (113809, 37641) 
0
source

Source: https://habr.com/ru/post/1447512/


All Articles