代码随想录算法训练营 day8 字符串part01

本文介绍了如何在Python中反转字符串,包括使用切片和理解字符串的不可变性。同时讨论了列表元素交换的方法,并指出在处理字符串中的空格问题时,正确的方法是删除所有空格后添加单个空格,而非仅保留一个。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

344. Reverse String

  • 见到字符串题目,多考虑双指针(同数组)
  • Python中没有内置的函数直接命名为反转字符串的功能(字符串本身不可变),但可以通过以下代码快速实现:(Copy到新空间,非原字符串)
reversed_str = original_str[::-1]
  • Python中,如果要交换List中的2个元素,请记住以下方法
lst[i], lst[j] = lst[j], lst[i]

  • ---------2504------------
  • 我本来写了一个swap函数,但发现字符数组s的元素并没有被交换,位置没变,后来经过查询得知:在C#中,字符(char)是值类型,按值传递会导致交换函数内的修改不影响原数组。正确的做法是通过索引直接修改数组中的元素。
    • 处理方法:直接在主函数中写交换,这个还真不好想到
    • public class Solution {
          public void ReverseString(char[] s) {
              // 注意:在C#中,字符(char)是值类型,按值传递会导致交换函数内的修改不影响原数组。正确的做法是通过索引直接修改数组中的元素。
              // Time:O(n), Space(1)
              for(int i = 0, j = s.Length - 1; i < j; i++, j--){
                  // swap_char(s[i] , s[j]);
                  char temp = s[i];
                  s[i] = s[j];
                  s[j] = temp;
              }
          }
      
          // public void swap_char(char s1, char s2){
          // 错误方法,交换了,但不影响原字符串s
          //     char temp = s1;
          //     s1 = s2;
          //     s2 = temp;
          // }
      }
    • 附:C#中超级简单的交换方法
    • (s[i], s[j]) = (s[j], s[i]);

541. Reverse String II

  • 卡尔:当成块操作时(每2K),直接在for循环条件设置 +2k。
  • Python中,s作为字符串不是常量吗?为什么还可以修改s?
s = s[:p] + s[p:p+k][::-1] + s[p+k:]

        在Python中,字符串确实是不可变(immutable)的,这意味着你不能修改字符串中的单个字符或者直接在原字符串上进行修改。然而,当你执行上方操作,你并没有直接修改原字符串s中的内容。相反,这个操作创建了一个新的字符串,它是由原字符串s的几个部分拼接而成的,包括一个被反转的子字符串。然后,这个新创建的字符串被赋值给了变量s。这是完全合法的,因为变量s可以被赋予任何字符串值,包括新构建的字符串。

这里的关键在于理解字符串不可变性和变量赋值之间的区别:

  • 字符串不可变性指的是字符串一旦创建,它的内容就不能被改变。例如,你不能通过索引直接修改字符串中的字符。

  • 变量赋值则是将一个对象(在这个例子中是一个字符串)关联到一个变量名上。变量可以被重新赋值,指向一个新的对象。在你的代码中,虽然s最初指向一个特定的字符串对象,但通过赋值操作,你可以让s指向一个全新的字符串对象。

  • ————2505——————

  • C#使用Span类型处理:

    Span<T> 是一种 内存安全且高性能的视图类型,用于高效地访问连续内存区域中的数据。在你的代码中,Span<char> 不是字符数组本身,而是对字符数组(char[])或字符串内存的视图(View),允许在不复制数据的前提下直接操作内存。

    详细解释:

  • Span<T> 是什么?

    • 类型定义Span<T> 是 .NET 中的一个结构体(struct),用于表示内存中一段连续的、类型为 T 的数据块
    • 作用:提供对数组、字符串、栈内存或非托管内存的安全访问,无需额外分配内存或复制数据
  • 代码中的 Span<char>

    Span<char> span = s.ToCharArray().AsSpan();
    • s.ToCharArray() 将字符串 s 转换为一个新的 char[] 数组。
    • AsSpan() 方法将该数组包装成一个 Span<char> 对象,表示对这个数组的视图。
    • 关键特性Span<char> 可以像数组一样通过索引访问字符,但直接在原数组上操作,不产生数据副本
  • 为什么使用 Span 而不是直接操作字符数组?

    • 性能优势Span 避免了内存复制,适合处理大字符串或高频操作。
    • 安全的内存访问Span 确保操作不会越界,避免内存安全问题。
    • 原地修改:在代码中调用 span[...].Reverse() 会在原数组上直接反转字符,无需创建新数组。
    • span[i..(i+k)].Reverse()
      • 通过 Span 的切片操作 i..(i+k),选取从索引 i 开始的 k 个字符。
      • 直接在原数组上调用 Reverse(),反转这些字符的位置,无需创建新数组
      • 这个操作的时间复杂度为 O(k/2),空间复杂度为 O(1),非常高效。
    • span[i..].Reverse() 是一个高效的原地反转操作

151. Reverse Words in a String

  • 本题较难。我看了3次视频,细品了超过30分钟
  • 这里快指针就是读指针,寻找下一个字母;慢指针是写指针,记录放在什么位置;
  • 老师的代码错了,第3个if应该是while。
  • 老师代码中,对于最下层的while,其负责处理一个单词
  • 老师代码中,对于while上的if,这里总是执行:
    • if的条件用于处理首个单词前(也是首个位置)不能有空格。
    • if内的语句用于给单词间增加1个空格。
  • 老师代码中,最外层的for和if,跳过了全部空格。因此,本题对于空格的处理思路:
    • 并不是:当空格多时,删掉多余的,只留一个
    • 而是:删掉了原字符串中的所有空格,再给单词间添加1个新空格。
  • B站网友提醒,参加笔试,完全可以最大程度使用库函数,包括一行秒。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值