I'm supposed to take a list of words and sort it, except I need to group all Strings that begin with 'x' first.
我应该取一个单词列表并对其进行排序,但是我需要将以“x”开头的所有字符串进行分组。
Here's what I got:
这是我得到的答案:
list_1 = []
list_2 = []
for word in words:
list_1.append(word) if word[0] == 'x' else list_2.append(word)
return sorted(list_1) + sorted(list_2)
But I have a feeling there is a much more elegant way to do this...
但我有一种感觉,有一种更优雅的方式来做这件事……
EDIT
编辑
Example: ['mix', 'xyz', 'apple', 'xanadu', 'aardvark']
yields ['xanadu', 'xyz', 'aardvark', 'apple', 'mix']
.
例子:[“混合”、“xyz”、“苹果”、“世外桃源”,“aardvark”)收益率(“世外桃源”、“xyz”、“豚”,“苹果”、“混合”)。
8 个解决方案
#1
41
>>> words = ['xoo', 'dsd', 'xdd']
>>> sorted(words, key=lambda x: (x[0] != 'x', x))
['xdd', 'xoo', 'dsd']
Explanation: the key function returns a pair (tuple). The first element is False
or True
, depending on whether the first char in the string is 'x'
. False
sorts before True
, so strings starting with 'x'
will be first in the sorted output. The second element in the tuple will be used to compare two elements that are the same in the first element, so all the strings starting with 'x'
will be sorted amongst themselves, and all the strings not starting with 'x'
will be sorted amongst themselves.
说明:键函数返回一对(元组)。第一个元素是False还是True,这取决于字符串中的第一个字符是否为“x”。False排序先于True,所以以x开头的字符串将在排序后的输出中首先出现。tuple中的第二个元素将用于比较第一个元素中相同的两个元素,因此以“x”开头的所有字符串将在它们之间排序,而不是以“x”开头的所有字符串将在它们之间排序。
#2
9
First: stop saying "pythonic" when you mean "clean". It's just a cheesy buzzword.
第一:当你说“干净”的时候,不要再说“毕达哥拉斯的”了。这只是一个俗气的流行语。
Don't use terniary expressions like that; it's meant to be used as part of an expression, not as flow control. This is cleaner:
不要用那种三元短语;它是用来作为表达式的一部分,而不是流控制。这是清洁:
for word in words:
if word[0] == 'x':
list_1.append(word)
else:
list_2.append(word)
You can improve it a bit more--using terniary expressions like this is fine:
你可以进一步改进它——使用像这样的三元表达就可以了:
for word in words:
target = list_1 if word[0] == 'x' else list_2
target.append(word)
If words
is a container and not an iterator, you could use:
如果单词是容器而不是迭代器,您可以使用:
list_1 = [word for word in words if word[0] == 'x']
list_2 = [word for word in words if word[0] != 'x']
Finally, we can scrap the whole thing, and instead use two sorts:
最后,我们可以抛弃整个东西,取而代之的是两种:
result = sorted(words)
result = sorted(result, key=lambda word: word[0] != 'x')
which first sorts normally, then uses the stable property of Python sorts to move words beginning with "x" to the front without otherwise changing the ordering.
通常先对其进行排序,然后使用Python排序的稳定属性将以“x”开头的单词移到前面,而不改变顺序。
#3
6
words = ['xoo', 'dsd', 'xdd']
list1 = [word for word in words if word[0] == 'x']
list2 = [word for word in words if word[0] != 'x']
#4
5
It should be noted that sorted
was added in Python 2.4 . If you would like a shorter version which is a bit cleaner and somewhat more backwards compatible you can alternatively use the .sort()
functionality directly off of list
. It should also be noted that empty strings will throw an exception when using x[0]
style array indexing syntax in this case (as many examples have). .startswith()
should be used instead, as is properly used in Tony Veijalainen's answer.
应该注意,在Python 2.4中添加了排序。如果您想要一个更简洁、向后兼容的更短的版本,您可以选择直接使用list之外的.sort()功能。还需要注意的是,在这种情况下,使用x[0]样式的数组索引语法时,空字符串将抛出一个异常(正如许多示例所做的那样)。
>>> words = ['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
>>> words.sort(key=lambda x: (not x.startswith('x'), x))
>>> words
['xanadu', 'xyz', '', 'aardvark', 'apple', 'mix']
The only disadvantage is that you're mutating the given object. This may be remedied by slicing the list beforehand.
唯一的缺点是你在改变给定的对象。这可以通过预先分割列表来补救。
>>> words = ['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
>>> new_words = words[:]
>>> new_words.sort(key=lambda x: (not x.startswith('x'), x))
>>> new_words
['xanadu', 'xyz', '', 'aardvark', 'apple', 'mix']
>>> words
['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
#5
2
words = ['xoo', 'dsd', 'xdd']
list1=filter(lambda word:word[0]=='x',words)
list2=filter(lambda word:word[0]!='x',words)
#6
2
To resend variation SilenGhosts code (feel free to copy, SilentGhost) as code not command prompt log
重新发送变体silenghost代码(请随意复制,SilentGhost)作为代码而不是命令提示日志
notinorder = ['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
print sorted(notinorder, key = lambda x: (not x.startswith('x'), x))
#7
1
>>> x = ['abc', 'xyz', 'bcd', 'xabc']
>>> y = [ele for ele in x if ele.startswith('x')]
>>> y
['xyz', 'xabc']
>>> z = [ele for ele in x if not ele.startswith('x')]
>>> z
['abc', 'bcd']
#8
0
More along the lines of your original solution:
更接近你最初的解决方案:
l1=[] l2=[] for w in sorted(words): (l1 if w[0] == 'x' else l2).append(w) l1.extend(l2) return l1
#1
41
>>> words = ['xoo', 'dsd', 'xdd']
>>> sorted(words, key=lambda x: (x[0] != 'x', x))
['xdd', 'xoo', 'dsd']
Explanation: the key function returns a pair (tuple). The first element is False
or True
, depending on whether the first char in the string is 'x'
. False
sorts before True
, so strings starting with 'x'
will be first in the sorted output. The second element in the tuple will be used to compare two elements that are the same in the first element, so all the strings starting with 'x'
will be sorted amongst themselves, and all the strings not starting with 'x'
will be sorted amongst themselves.
说明:键函数返回一对(元组)。第一个元素是False还是True,这取决于字符串中的第一个字符是否为“x”。False排序先于True,所以以x开头的字符串将在排序后的输出中首先出现。tuple中的第二个元素将用于比较第一个元素中相同的两个元素,因此以“x”开头的所有字符串将在它们之间排序,而不是以“x”开头的所有字符串将在它们之间排序。
#2
9
First: stop saying "pythonic" when you mean "clean". It's just a cheesy buzzword.
第一:当你说“干净”的时候,不要再说“毕达哥拉斯的”了。这只是一个俗气的流行语。
Don't use terniary expressions like that; it's meant to be used as part of an expression, not as flow control. This is cleaner:
不要用那种三元短语;它是用来作为表达式的一部分,而不是流控制。这是清洁:
for word in words:
if word[0] == 'x':
list_1.append(word)
else:
list_2.append(word)
You can improve it a bit more--using terniary expressions like this is fine:
你可以进一步改进它——使用像这样的三元表达就可以了:
for word in words:
target = list_1 if word[0] == 'x' else list_2
target.append(word)
If words
is a container and not an iterator, you could use:
如果单词是容器而不是迭代器,您可以使用:
list_1 = [word for word in words if word[0] == 'x']
list_2 = [word for word in words if word[0] != 'x']
Finally, we can scrap the whole thing, and instead use two sorts:
最后,我们可以抛弃整个东西,取而代之的是两种:
result = sorted(words)
result = sorted(result, key=lambda word: word[0] != 'x')
which first sorts normally, then uses the stable property of Python sorts to move words beginning with "x" to the front without otherwise changing the ordering.
通常先对其进行排序,然后使用Python排序的稳定属性将以“x”开头的单词移到前面,而不改变顺序。
#3
6
words = ['xoo', 'dsd', 'xdd']
list1 = [word for word in words if word[0] == 'x']
list2 = [word for word in words if word[0] != 'x']
#4
5
It should be noted that sorted
was added in Python 2.4 . If you would like a shorter version which is a bit cleaner and somewhat more backwards compatible you can alternatively use the .sort()
functionality directly off of list
. It should also be noted that empty strings will throw an exception when using x[0]
style array indexing syntax in this case (as many examples have). .startswith()
should be used instead, as is properly used in Tony Veijalainen's answer.
应该注意,在Python 2.4中添加了排序。如果您想要一个更简洁、向后兼容的更短的版本,您可以选择直接使用list之外的.sort()功能。还需要注意的是,在这种情况下,使用x[0]样式的数组索引语法时,空字符串将抛出一个异常(正如许多示例所做的那样)。
>>> words = ['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
>>> words.sort(key=lambda x: (not x.startswith('x'), x))
>>> words
['xanadu', 'xyz', '', 'aardvark', 'apple', 'mix']
The only disadvantage is that you're mutating the given object. This may be remedied by slicing the list beforehand.
唯一的缺点是你在改变给定的对象。这可以通过预先分割列表来补救。
>>> words = ['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
>>> new_words = words[:]
>>> new_words.sort(key=lambda x: (not x.startswith('x'), x))
>>> new_words
['xanadu', 'xyz', '', 'aardvark', 'apple', 'mix']
>>> words
['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
#5
2
words = ['xoo', 'dsd', 'xdd']
list1=filter(lambda word:word[0]=='x',words)
list2=filter(lambda word:word[0]!='x',words)
#6
2
To resend variation SilenGhosts code (feel free to copy, SilentGhost) as code not command prompt log
重新发送变体silenghost代码(请随意复制,SilentGhost)作为代码而不是命令提示日志
notinorder = ['mix', 'xyz', '', 'apple', 'xanadu', 'aardvark']
print sorted(notinorder, key = lambda x: (not x.startswith('x'), x))
#7
1
>>> x = ['abc', 'xyz', 'bcd', 'xabc']
>>> y = [ele for ele in x if ele.startswith('x')]
>>> y
['xyz', 'xabc']
>>> z = [ele for ele in x if not ele.startswith('x')]
>>> z
['abc', 'bcd']
#8
0
More along the lines of your original solution:
更接近你最初的解决方案:
l1=[] l2=[] for w in sorted(words): (l1 if w[0] == 'x' else l2).append(w) l1.extend(l2) return l1