2024/12/14 【字符串】LeetCode151.反转字符串中的单词 【√】知识点:几个易错点,split函数
编程实现了Python中split函数的简单分割功能
class Solution: def mySplit(self, s: str) -> list: n = len(s) i = 0 s_list = [] while i < n: min_s = "" while i < n and s[i] == " ": i += 1 while i < n and s[i] != " ": min_s += s[i] i += 1 if min_s != "": s_list.append(min_s) return s_list def reverseWords(self, s: str) -> str: s_list = self.mySplit(s) s_list.reverse() s = "" n = len(s_list) for i in range(n-1): s += s_list[i] + " " s += s_list[-1] return s
时间复杂度:
mySplit
方法:O(n)reverseWords
方法:O(n)(包含mySplit
的调用和字符串拼接)
空间复杂度:
mySplit
方法:O(n)reverseWords
方法:O(n)
因此,整体时间复杂度和空间复杂度都是 O(n),其中 n 是字符串 s
的长度。
注意如下几点:
1,在mySplit函数中,
while i < n and s[i] == " ":
如果你把 while i < n and s[i] != " "
里的两个条件颠倒,变成 while s[i] != " " and i < n
,会报错的原因是 逻辑错误导致数组越界。
原因:
while i < n and s[i] != " "
的条件顺序是正确的。它首先检查 i < n
,确保索引 i
在有效范围内,然后再检查 s[i] != " "
,即当前字符是否不是空格。这样,i
不会超出字符串的长度。
然而,当你把这两个条件的顺序调换成 while s[i] != " " and i < n
时,问题出现在对 i
的检查上。因为条件的顺序被颠倒了,s[i] != " "
会先被检查,在访问 s[i]
时如果 i
已经超出了字符串的范围(即 i >= n
),会发生 索引越界 错误(IndexError
)。
2.要加入判断
if min_s != "": s_list.append(min_s)
如果输入字符串的末尾是空格,或者存在多个连续空格,min_s
会变成空字符串 ""
。你仍然会把这个空字符串添加到 s_list
中,导致 s_list
中可能会有多余的空字符串。
3.reverse函数
s_list = self.mySplit(s) s_list = s_list.reverse() n = len(s_list)
这段代码会报错,因为reverse函数没有返回值,此时s_list为NoneType类型,没办法用len函数。
NoneType
是 Python 中一个特殊的类型,表示“没有值”或“空值”。len()
是用来获取对象(如字符串、列表、元组等)长度的函数,但它不能用于None
类型的对象。
reverse()
是 Python 中列表 (list
) 类型的方法,用于就地反转列表中的元素。这意味着该方法不会返回一个新的列表,而是直接修改原列表。
参数:
reverse()
方法没有任何参数。
返回值:
reverse()
方法没有返回值。它直接修改原列表,将列表中的元素顺序反转。
示例:
-
包含不同数据类型的列表:
lst = [1, "hello", 3.14, True] lst.reverse() print(lst) # 输出:[True, 3.14, 'hello', 1]
注意事项:
-
reverse()
是 就地 修改列表的,它不会返回新的列表。也就是说,它直接在原始列表上修改数据,所以如果你需要保留原始列表,可以先创建一个副本。lst = [1, 2, 3] lst_copy = lst.copy() # 创建副本 lst_copy.reverse() # 反转副本 print(lst) # 输出:[1, 2, 3] print(lst_copy) # 输出:[3, 2, 1]
-
reverse()
只能用于 列表类型,如果你尝试对其他类型(如字符串或元组)使用该方法,会报错。s = "hello" s.reverse() # 会抛出 AttributeError: 'str' object has no attribute 'reverse'
reversed()
函数(区别于 reverse()
):
- 如果你想反转一个列表并返回一个新的列表而不修改原列表,可以使用
reversed()
函数。lst = [1, 2, 3, 4, 5] reversed_lst = list(reversed(lst)) # 反转并返回新列表 print(reversed_lst) # 输出:[5, 4, 3, 2, 1]
4.split函数
split()
是 Python 中字符串对象的一个方法,用于将字符串分割成多个子字符串,并返回一个列表。默认情况下,它根据空白字符(如空格、换行符、制表符等)进行分割,但你也可以指定分隔符来进行自定义分割。
语法:
string.split([separator[, maxsplit]])
参数:
- separator:可选,指定分隔符,默认值是
None
,意味着按任意空白字符(空格、换行符等)分割。 - maxsplit:可选,指定分割的最大次数。如果指定了
maxsplit
,则最多分割maxsplit
次,剩余部分会作为一个单独的元素返回。
示例:
-
默认按空格分割:
text = "hello world python" result = text.split() print(result) # 输出:['hello', 'world', 'python']
-
指定分隔符:
text = "apple,orange,banana" result = text.split(',') print(result) # 输出:['apple', 'orange', 'banana']
-
限制分割次数:
text = "apple orange banana grape" result = text.split(' ', 2) print(result) # 输出:['apple', 'orange', 'banana grape']
-
分割时空白字符被忽略:
text = " hello world " result = text.split() print(result) # 输出:['hello', 'world']
这个方法非常实用,尤其是在处理以特定符号分隔的字符串时。
代码随想录解法:
不要使用辅助空间,空间复杂度要求为O(1)。
(版本一)先删除空白,然后整个反转,最后单词反转。 因为字符串是不可变类型,所以反转单词的时候,需要将其转换成列表,然后通过join函数再将其转换成列表,所以空间复杂度不是O(1)
class Solution: def reverseWords(self, s: str) -> str: # 删除前后空白 s = s.strip() # 反转整个字符串 s = s[::-1] # 将字符串拆分为单词,并反转每个单词 s = ' '.join(word[::-1] for word in s.split()) return s
1. strip函数和split函数
strip()
和 split()
都是 Python 字符串方法,它们用于处理字符串,但有不同的功能和用途。我们来分别解释它们。
(1). strip()
函数
作用:
strip()
用于去除字符串两端(开头和结尾)的指定字符,默认去除空白字符(包括空格、换行符 \n
、制表符 \t
等)。
语法:
string.strip([chars])
-
参数:
chars
(可选):指定要去除的字符集合。如果不传入参数,默认为去除空白字符。
-
返回值:
- 返回一个新的字符串,去除了两端的指定字符。
示例:
-
去除两端空白字符:
s = " Hello, World! " print(s.strip()) # 输出:'Hello, World!'
-
去除两端的特定字符:
s = "****Hello, World!****" print(s.strip('*')) # 输出:'Hello, World!'
-
去除换行符:
s = "\nHello, World!\n" print(s.strip()) # 输出:'Hello, World!'
(2). split()
函数
作用:
split()
用于将字符串分割成一个列表,分割的依据是指定的分隔符,默认为空白字符(空格、制表符、换行符等)。
示例:
-
按空格分割:
s = "Hello World from Python" print(s.split()) # 输出:['Hello', 'World', 'from', 'Python']
-
按指定字符分割:
s = "apple,banana,cherry" print(s.split(',')) # 输出:['apple', 'banana', 'cherry']
-
限制分割次数:
s = "apple banana cherry grape" print(s.split(' ', 2)) # 输出:['apple', 'banana', 'cherry grape']
-
分割空白字符(包括多个空格):
s = " Hello World from Python " print(s.split()) # 输出:['Hello', 'World', 'from', 'Python']
在这种情况下,
split()
会自动忽略连续的空白字符,并且不会在返回的列表中包含空字符串。
总结对比:
函数 | 作用 | 默认行为 | 示例 |
---|---|---|---|
strip() |
去除字符串两端的空白字符或指定字符 | 去除两端的空白字符(空格、换行符、制表符等) | s = " Hello " 结果为 "Hello" |
split() |
将字符串按指定分隔符分割成列表 | 默认按空白字符分割,忽略多个连续空白字符 | s = "Hello World" 结果为 ['Hello', 'World'] |
使用场景:
- 使用
strip()
当你需要去除字符串两端的空白字符或特定字符时。 - 使用
split()
当你需要将一个字符串按分隔符拆分为多个子字符串时。
2.''.join()
''.join()
是 Python 字符串的一个方法,用于将一个可迭代对象(如列表、元组、字符串等)中的元素连接成一个新的字符串。特别地,''
(空字符串)作为连接符表示各个元素之间没有任何分隔符,直接连接。
语法:
''.join(iterable)
- 参数:
iterable
:可以是一个包含字符串元素的可迭代对象(如列表、元组、集合等)。注意,iterable
中的每个元素必须是字符串类型。
- 返回值:
- 返回一个新的字符串,连接了
iterable
中的所有元素
- 返回一个新的字符串,连接了
版本二:拆分字符串+反转列表
class Solution: def reverseWords(self, s): words = s.split() #type(words) --- list words = words[::-1] # 反转单词 return ' '.join(words) #列表转换成字符串