这一直让我困惑。看起来这样会更好:

["Hello", "world"].join("-")

除此之外:

"-".join(["Hello", "world"])

有什么具体的原因吗?


当前回答

主要是因为someString.jjoin()的结果是字符串。

序列(列表或元组等)不会出现在结果中,只是一个字符串。因为结果是一个字符串,所以它作为字符串的方法是有意义的。

其他回答

这在String方法中讨论过。。。最后一个线程,并被Guido接受。该线程始于1999年6月,str.join包含在2000年9月发布的Python 1.6中(支持Unicode)。Python 2.0(支持str方法,包括join)于2000年10月发布。

本主题提出了四个选项:str.join(seq)顺序连接(str)顺序减少(str)作为内置函数连接Guido希望不仅支持列表和元组,而且支持所有序列/可迭代项。seq.reduce(str)对于新手来说很难。join(str)引入了从序列到str/unicode的意外依赖关系。join()作为独立的内置函数将只支持特定的数据类型。因此,使用内置命名空间是不好的。如果join()支持许多数据类型,那么创建一个优化的实现将是困难的:如果使用__add__方法实现,那么它将是O(n²)。分隔符字符串(sep)不应省略。显式优于隐式。

以下是一些额外的想法(我自己和我朋友的):

Unicode支持即将到来,但还不是最终的。当时UTF-8最有可能取代UCS-2/-4。要计算UTF-8字符串的总缓冲区长度,该方法需要知道字符编码。当时,Python已经决定了一个通用的序列接口规则,用户可以在其中创建一个类似序列的(可迭代的)类。但Python直到2.2才支持扩展内置类型。当时很难提供基本的可迭代类(这在另一条评论中提到)。

Guido的决定记录在历史邮件中,决定str.join(seq):

有趣,但看起来确实没错!巴里,去吧。。。吉多·范罗苏姆

变量my_list和“-”都是对象。具体来说,它们分别是类列表和str的实例。join函数属于str类。因此,使用语法“-”.join(my_list)是因为对象“-”将my_list作为输入。

-join(my_list)声明您正在从列表中的连接元素转换为字符串。它是面向结果的。(仅为便于记忆和理解)

我做了一份详尽的方法清单,供你参考。

string_methods_44 = {
    'convert': ['join','split', 'rsplit','splitlines', 'partition', 'rpartition'],
    'edit': ['replace', 'lstrip', 'rstrip', 'strip'],
    'search': ['endswith', 'startswith', 'count', 'index', 'find','rindex', 'rfind',],
    'condition': ['isalnum', 'isalpha', 'isdecimal', 'isdigit', 'isnumeric','isidentifier',
                  'islower','istitle', 'isupper','isprintable', 'isspace', ],
    'text': ['lower', 'upper', 'capitalize', 'title', 'swapcase',
             'center', 'ljust', 'rjust', 'zfill', 'expandtabs','casefold'],
    'encode': ['translate', 'maketrans', 'encode'],
    'format': ['format', 'format_map']}

将其视为拆分的自然正交操作。

我明白为什么它适用于任何可迭代的东西,所以不能简单地在列表中实现。

为了可读性,我希望在语言中看到它,但我认为这实际上是不可行的-如果可迭代性是一个接口,那么它可以添加到接口中,但这只是一个约定,因此没有中心方法将它添加到可迭代的一组东西中。

你不能只加入列表和元组。您可以加入几乎任何可迭代的。可迭代的包括生成器、映射、过滤器等

>>> '-'.join(chr(x) for x in range(48, 55))
'0-1-2-3-4-5-6'

>>> '-'.join(map(str, (1, 10, 100)))
'1-10-100'

使用生成器、地图、过滤器等的好处是它们几乎不需要内存,而且几乎是即时创建的。

这只是概念上的另一个原因:

str.join(<iterator>)

只有赋予str这种能力才有效。而不是向所有迭代器授予联接:列表、元组、集合、字典、生成器、映射、过滤器,所有这些迭代器都只有对象作为公共父对象。

当然,range()和zip()也是迭代器,但它们永远不会返回str,因此不能与str.jjoin()一起使用

>>> '-'.join(range(48, 55))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: sequence item 0: expected str instance, int found