简体   繁体   中英

How can I use lambda to count the number of words in a file?

I'm trying to calculate the number of words in a file using reduce , lambda & readlines in an unconventional way:

import functools as ft
f=open("test_file.txt")
words=ft.reduce(lambda a,b:(len(a.split())+len(b.split())),f.readlines())
print(words)

This raises an attribute error as I'm trying to split integers (indices). How do I get this code to split the elements of the iterable returned by f.readlines() and successively add their lengths (ie, number of words in those lines) to ultimately calculate the total number of words in the file?

If you're trying get a count of words in a file, f.read() makes more sense than f.readlines() because it obviates the need to sum line-by-line counts. You get the whole file in a chunk and can then split on whitespace using split without arguments.

>>> with open("foo.py") as f:
...     len(f.read().split())
...
1530

If you really want to use readlines , it's easier to avoid functools.reduce in any event and sum the lengths of the split lines ( sum is a very succinct reduction operation on an iterable that does away with the distracting accumulator business):

>>> with open("foo.py") as f:
...     sum(len(x.split()) for x in f.readlines())
...
1530

It's good practice to use a with context manager so your resource is automatically closed. Use whitespace around all operators so the code is readable.

As for getting functools.reduce to work: it accepts a lambda which accepts the accumulator as its first argument and the current element as the second. The second argument to functools.reduce is an iterable and the third initializes the accumulator. Leaving it blank as you've done sets it to the value of the first item in the iterable--probably not what you want, since the idea is to perform a numerical summation using the accumulator.

You can use

>>> with open("foo.py") as f:
...     ft.reduce(lambda acc, line: len(line.split()) + acc, f.readlines(), 0)
...
1530

but this strikes me as a rather Rube Goldbergian way to solve the problem.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM