简体   繁体   中英

Using list comprehension and sets

Create and print a list of words for which both the following criteria are all met:

  • the word is at least 8 characters long;
  • the word formed from the odd-numbered letter is in the set of lower-case words; and
  • the word formed from the even-numbered letters is in the set of lower-case words.

For example, the word "ballooned" should be included in your list because the word formed from the odd-numbered letters, "blond", and the word formed from the even-numbered letters, "aloe", are both in the set of lower-case words. Similarly, "triennially" splits into "tinily" and "renal", both of which are in the word list.

My teacher told us we should use a set: s=set(lowers) because this would be faster.

what i have so far:

s=set(lowers)
[word for word in lowers if len(word)>=8
                        and list(word)(::2) in s
                        and list(word)(::-2) in s]

I do not think I am using the set right. can someone help me get this to work

The problem is that you cast word to a list (unnecessary), your slices are not in brackets (you used parenthesis), and your second slice uses the wrong indices (should be 1::2 , not ::-2 ).

Here are the slices done correctly:

>>> word = "ballooned"
>>> word[::2]
'blond'
>>> word[1::2]
'aloe'

Note that s is an odd name for a collection of lowercase words. A better name would be words .

Your use of set is correct. The reason your teacher wants you to use a set is it is much faster to test membership of a set than it is for a list.

Putting it together:

words = set(lowers)
[word for word in words if len(word) >= 8
                        and word[::2] in words
                        and word[1::2] in words]

Here is a quick example of how to structure your condition check inside of the list comprehension:

>>> word = 'ballooned'
>>> lowers = ['blond', 'aloe']
>>> s = set(lowers)
>>> len(word) >= 8 and word[::2] in s and word[1::2] in s
True

edit: Just realized that lowers contains both the valid words and the "search" words like 'ballooned' and 'triennially', in any case you should be able to use the above condition inside of your list comprehension to get the correct result.

list(word)(::2)

First, the syntax to access index ranges is using squared parentheses, also, you don't need to cast word to a list first, you can directly do that on the string:

>>> 'ballooned'[::2]
'blond'

Also, [::-2] won't give you the uneven word, but a reversed version of the other one. You need to use [1::2] (ie skip the first, and then every second character):

>>> 'ballooned'[::-2]
'dnolb'
>>> 'ballooned'[1::2]
'aloe'

In general it is always a good idea to test certain parts separately to see if they really do what you think they do.

this should do it:

s=set(lowers)
[word for word in lowers if len(word)>=8 and word[::2] in s and word[1::2] in s]

or using all() :

In [166]: [word for word in lowers if all((len(word)>=8,
                                               word[::2] in s,
                                               word[1::2] in s))]

use [::] not (::) and there's no need of list() here, plus to get the word formed by letters placed at odd position use [1::2] .

In [151]: "ballooned"[::2]
Out[151]: 'blond'

In [152]: "ballooned"[1::2]
Out[152]: 'aloe'

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