如何在不使用C括号的情况下修改字符串文字的内容? 堆栈内存堆内存

如何解决如何在不使用C括号的情况下修改字符串文字的内容? 堆栈内存堆内存

免责声明:这是一项家庭作业。

说我有一个这样声明的字符串:

char *string1;

对于我的程序的一部分,我需要将string1设置为另一个字符串string2。我不能使用strcpy或括号。

到目前为止,这是我的代码:

int i;
for(i = 0; *(string2 + i) != '\0'; i++){
    *(string1 + i) = *(string2 + i);
}

这会导致分段错误。 根据{{​​3}}的说法,这是因为string1的声明是这样的:char *string1,一种避免段错误的解决方法是使用方括号。我不能使用方括号,所以有什么解决方法吗?

编辑:我也被禁止分配更多的内存或声明数组。我不能使用malloc(),falloc()等。

解决方法

您遇到的问题是string2没有为其分配内存。

您的代码缺少一些细节,但是我认为它看起来像这样:

#include <stdio.h>

int main()
{
  char *originalStr = "Hello NewArsenic";
  char *newStr;

  // YMMV depending on the compiler for this line. Might print (null) for
  // newStr or it might throw an error.
  printf("Original: %s\nNew: %s\n",originalStr,newStr);

  int i;
  for (i = 0; *(originalStr + i) != '\0'; i++)
  {
    *(newStr + i) = *(originalStr + i);
  }

  printf("Original: %s\nNew: %s\n",newStr);

  return 0;
}

TL; DR您的问题

这里的问题是,您试图在没有足够内存的情况下将某些值存储到newStr中。

解决方案

使用malloc

#include <stdio.h>
#include <stdlib.h> // malloc(size_t) is in stdlib.h
#include <string.h> // strlen(const char *) is in string.h

int main()
{
  char *originalStr = "Hello NewArsenic";

  // Note here that size_t is preferable to int for length.
  // Generally you want to be using size_t if you are working with size/length.
  // More info at https://stackoverflow.com/questions/19732319/difference-between-size-t-and-unsigned-int
  size_t originalLength = strlen(originalStr);

  // This is malloc's typical usage,where we are asking from the system to
  // give us originalLength + 1 many chars.
  // The `char` here is redundant,actually,since sizeof(char) is defined to
  // be one by the C spec,but you might find it useful to see the typical
  // usage of `malloc`.
  // Since malloc returns a void *,we need to cast that to a char *.
  char *newStr = (char *)malloc((originalLength + 1) * sizeof(char));

  // Your code stays the same.
  printf("Original: %s\nNew: %s\n",newStr);

  size_t i;
  for (i = 0; *(originalStr + i) != '\0'; i++)
  {
    *(newStr + i) = *(originalStr + i);
  }

  // Don't forget to append a null character like I did before editing!
  *(newStr + originalLength) = 0;

  printf("Original: %s\nNew: %s\n",newStr);

  // Because `malloc` gives us memory on the stack,we need to tell the system
  // that we want to free it before exiting.
  free(newStr);

  return 0;
}

长答案

什么是C字符串?

在C中,字符串仅仅是字符数组。这意味着对于每个想要拥有的字符,您都需要分配内存。

内存

在C语言中,有两种类型的内存分配-基于堆栈的和基于堆的。

堆栈内存

您可能比您想象的更熟悉基于堆栈的内存。每当声明变量时,就在堆栈上定义它。用括号表示法type array[size_t]声明的数组也是基于堆栈的。基于堆栈的内存分配的特定之处在于,当您分配内存时,它可能只会持续使用声明它的函数的时间,这可能是您熟悉的。这意味着您不必担心内存停留的时间比实际需要的时间长。

堆内存

现在基于堆的内存分配有所不同,因为它将一直持续到清除为止。这是一种优势:

  • 您可以保留在编译时不知道其大小的值。 但是,这是有代价的:
  • 堆比较慢
  • 完成操作后,您必须手动清除内存。

有关更多信息,请查看this线程。

我们通常使用函数(void *) malloc(size_t)及其姐妹(void *) calloc(size_t,size_t)来分配堆内存。要释放系统要求的内存,请使用free(void *)

替代品

您也可以使用newStr = originalStr,但是实际上并不会复制字符串,而只是使newStr指向originalStr,我相信您已经知道

其他备注

  • 通常,这是一种反模式:
char* string = "literal";

这是一个反模式,因为不能编辑文字,也不能编辑文字。做:

char const* string = "literal";

有关更多信息,请参见this线程。

  • 避免在循环中使用int。使用size_t参见this线程。
,

对于我的程序的一部分,我需要将string1设置为另一个字符串string2。我不能使用strcpy或括号。

也许解决方案就像

string2 = string1

请注意,这会将string2指针分配为直接指向与string1相同的内存。有时候这很有用,因为您需要使用string1来保持字符串的开头,但是还需要另一个指针来使用string2++这样的字符串来移动字符串。

以一种或另一种方式,您必须将string2指向您可以访问的内存中的地址。有两种方法可以做到这一点:

  1. 指向您已经可以通过另一个变量(具有另一个指针变量或&运算符的地址)访问的内存。

  2. 使用malloc()或相关功能分配内存。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


使用本地python环境可以成功执行 import pandas as pd import matplotlib.pyplot as plt # 设置字体 plt.rcParams[&#39;font.sans-serif&#39;] = [&#39;SimHei&#39;] # 能正确显示负号 p
错误1:Request method ‘DELETE‘ not supported 错误还原:controller层有一个接口,访问该接口时报错:Request method ‘DELETE‘ not supported 错误原因:没有接收到前端传入的参数,修改为如下 参考 错误2:cannot r
错误1:启动docker镜像时报错:Error response from daemon: driver failed programming external connectivity on endpoint quirky_allen 解决方法:重启docker -&gt; systemctl r
错误1:private field ‘xxx‘ is never assigned 按Altʾnter快捷键,选择第2项 参考:https://blog.csdn.net/shi_hong_fei_hei/article/details/88814070 错误2:启动时报错,不能找到主启动类 #
报错如下,通过源不能下载,最后警告pip需升级版本 Requirement already satisfied: pip in c:\users\ychen\appdata\local\programs\python\python310\lib\site-packages (22.0.4) Coll
错误1:maven打包报错 错误还原:使用maven打包项目时报错如下 [ERROR] Failed to execute goal org.apache.maven.plugins:maven-resources-plugin:3.2.0:resources (default-resources)
错误1:服务调用时报错 服务消费者模块assess通过openFeign调用服务提供者模块hires 如下为服务提供者模块hires的控制层接口 @RestController @RequestMapping(&quot;/hires&quot;) public class FeignControl
错误1:运行项目后报如下错误 解决方案 报错2:Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:3.8.1:compile (default-compile) on project sb 解决方案:在pom.
参考 错误原因 过滤器或拦截器在生效时,redisTemplate还没有注入 解决方案:在注入容器时就生效 @Component //项目运行时就注入Spring容器 public class RedisBean { @Resource private RedisTemplate&lt;String
使用vite构建项目报错 C:\Users\ychen\work&gt;npm init @vitejs/app @vitejs/create-app is deprecated, use npm init vite instead C:\Users\ychen\AppData\Local\npm-
参考1 参考2 解决方案 # 点击安装源 协议选择 http:// 路径填写 mirrors.aliyun.com/centos/8.3.2011/BaseOS/x86_64/os URL类型 软件库URL 其他路径 # 版本 7 mirrors.aliyun.com/centos/7/os/x86
报错1 [root@slave1 data_mocker]# kafka-console-consumer.sh --bootstrap-server slave1:9092 --topic topic_db [2023-12-19 18:31:12,770] WARN [Consumer clie
错误1 # 重写数据 hive (edu)&gt; insert overwrite table dwd_trade_cart_add_inc &gt; select data.id, &gt; data.user_id, &gt; data.course_id, &gt; date_format(
错误1 hive (edu)&gt; insert into huanhuan values(1,&#39;haoge&#39;); Query ID = root_20240110071417_fe1517ad-3607-41f4-bdcf-d00b98ac443e Total jobs = 1
报错1:执行到如下就不执行了,没有显示Successfully registered new MBean. [root@slave1 bin]# /usr/local/software/flume-1.9.0/bin/flume-ng agent -n a1 -c /usr/local/softwa
虚拟及没有启动任何服务器查看jps会显示jps,如果没有显示任何东西 [root@slave2 ~]# jps 9647 Jps 解决方案 # 进入/tmp查看 [root@slave1 dfs]# cd /tmp [root@slave1 tmp]# ll 总用量 48 drwxr-xr-x. 2
报错1 hive&gt; show databases; OK Failed with exception java.io.IOException:java.lang.RuntimeException: Error in configuring object Time taken: 0.474 se
报错1 [root@localhost ~]# vim -bash: vim: 未找到命令 安装vim yum -y install vim* # 查看是否安装成功 [root@hadoop01 hadoop]# rpm -qa |grep vim vim-X11-7.4.629-8.el7_9.x
修改hadoop配置 vi /usr/local/software/hadoop-2.9.2/etc/hadoop/yarn-site.xml # 添加如下 &lt;configuration&gt; &lt;property&gt; &lt;name&gt;yarn.nodemanager.res