【问题标题】:Read a string char by char from an associative pointer array从关联指针数组中逐字符读取字符串
【发布时间】:2019-01-19 21:12:23
【问题描述】:

已解决

我创建一个新的char *ch malloc(strlen) 并逐个字符地循环该字符串。然后我使用memcpy(ch, &stringpool[index], len) 将其复制回来当然,之后free(ch)


我希望我的问题的标题是正确的。

我有一个字符串池

char **string_pool;

在类似的函数中启动

string_pool = malloc( sizeof(char *) * 1024);

我从标准输入获取字符串并将它们扫描到数组中

scanf("%[^\n]s", &string_pool[index]);

所以我可以使用 printf 打印出来

printf("gets %s\n", &string_pool[index]);

我该怎么做

  • 获取string_pool[index]的长度
  • 在循环中逐个字符读取 string_pool[index] 字符

谢谢

编辑

也许我应该多解释一下,它是一个带有虚拟指令集和类似程序的虚拟机

push 1
read
gets

应该:

  • 将 1 压入堆栈 -> 让 x 为 1
  • 将标准输入作为字符串读入 string_pool[x]
  • 将所有字符压入堆栈

函数看起来像

    case GETS: {
        int index = popv(); // index is already on top of the stack
        int strl = strlen(&string_pool[index]);

        printf("gets %s with a length of %d\n", &string_pool[index], strl);
        // pseudo code
        // push each char as integer on the stack
        foreach(char in string_pool[index]) push((int)char);

        break;
    }

    case READ: {  
        int index = popv();          
        scanf("%[^\n]s", &string_pool[index]);
        break;
    }

    case WRITE: {  
        int index = popv();          
        printf("%s", &string_pool[index]);
        break;
    }

我的问题是在GETS 案例中。我想将每个 char 作为 int 推入堆栈。

【问题讨论】:

  • 使用strlen()有什么问题?
  • 当我使用 strlen(&string_pool[i]) 我得到一个编译器错误expected 'const char *' but argument is of type 'char **'
  • scanf("%[^\n]s", string_pool[index]); 将导致未定义的行为,因为您没有为 string_pool[index] 分配任何空间。
  • 请出示 MCVE (minimal reproducible example)。目前尚不清楚您的编辑要做什么。
  • 您的实际问题是什么?你有什么问题?标题是一个指令,而不是一个问题。

标签: c arrays string pointers


【解决方案1】:
char **string_pool;
string_pool = malloc( sizeof(char *) * 1024);

分配 1024 个 pointers-to-char。 (string_poolpointer-to-pointer-to-char)每个指针都未初始化并且指向没有可用的有效存储。在使用每个指针之前,您必须通过分配内存并将起始地址分配给每个指针(以便每个指针“指向”有效内存)来使它们指向有效内存。

为了允许对您读取的每个字符串进行适当的大小调整和分配,您可以使用 fgets 和一个足以存储您期望的最长输入的固定缓冲区,或者您可以使用 POSIX getline,它将为输入分配存储空间必需的。使用 fgets 你会做类似的事情:

#define MAXCHR 2048
...

char buffer[MAXCHR];

fputs ("enter string: ", stdout);
if (fgets (buffer, MAXCHR, stdin) == NULL) {
    fputs ("(user canceled input.)\n", stderr);
    return 1;
}

size_t len = strlen (buffer);   /* get the length of input (with '\n') */
if (len && buffer[len - 1] == '\n')    /* trim the '\n' from end */
    buffer[--len] = 0;          /* by overwriting with nul-character */


string_pool[index] = malloc (len + 1);      /* allocate storage for buffer */
if (string_pool[index] == NULL) {           /* validate allocation */
    perror ("maklloc-string_pool[index]");  /* handle error */
    return 1;  /* or break read loop; */
}
/* copy buffer to string_pool[index], advance index */
memcpy (string_pool[index++], buffer, len + 1); 

您通常会在您的读取循环中执行此操作,只允许输入 while index < 1024 以确保您不会尝试为一个指针分配过多的存储空间。

检查一下,如果您有任何问题,请告诉我。

【讨论】:

  • 我正在寻找另一个方向 - 获取已存储的字符串
  • 没问题,那么您只需将已存储字符串的地址分配给您的string_pool[index] 指针。由于您有1024 指针,因此可以通过简单的赋值使它们指向您已有的任何有效字符串。 (但请注意,在赋值之后,如果指针指向的内容超出范围,则尝试通过指针引用字符串将导致 Undefined Behavior
  • 请再次阅读我编辑的问题。看案例:最后一个代码块中的GETS语句
  • 好吧,我还是觉得你在混淆指针和堆栈存储等。例如,scanf("%[^\n]s", &string_pool[index]); 是无效的。 string_pool[index]char* 类型(对应于指针类型 %[...] 需要)。当您尝试使用&string_pool[index]) 时,即键入char** 并调用未定义的行为。当您使用scanf(我在上面替换为fgets)阅读时,您必须拥有存储所读取内容的存储空间。尝试混合保留和推送到堆栈的程序集语义掩盖了所有字符串将具有相同地址的事实。
  • 我也认为你是对的:P 我通过创建一个大小为 (strlen) 的缓冲区并用 memcpy 复制它来解决它,你指出我的方向 +1,对不起
【解决方案2】:

您必须为每个字符串分配空间。 所以,例如,

string_pool[0] = malloc( 100 );

然后将允许您将长达 99 个字符的字符串读取到 string_pool[0] 中(终止 null 需要额外的空间)。

【讨论】:

  • 每次插入新数组时都必须这样做吗?所以如果已经有3个数组,我必须做string_pool[3] = mallog(strlen)
  • 是的,您必须为数组中的每个字符串分配空间。您原来的 malloc 只为指针分配空间,在您为每个指针创建空间之前,这些指针保持未初始化。
  • 我不明白这怎么属于我的问题。我存储字符串没有问题,我的问题是读取它们
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-08-20
  • 2021-06-28
  • 1970-01-01
  • 2010-11-08
  • 1970-01-01
  • 2012-09-29
相关资源
最近更新 更多