发出访问C中字符指针数组的内容

时间:2015-03-12 20:33:09

标签: c arrays pointers

我正在阅读K& R的C编程语言,并尝试理解字符指针和数组。

我在C中创建一个函数,它从stdin读取多行,并将行(char*)存储在一个字符指针数组中(char* [])。

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

enum {MAXINPUT = 1024, MAXLINES = 100};

/* Reads at most `maxLines` lines and stores them in an array of char pointers. Returns number of lines read. */
int readlines(char* lineptr[], int maxLines);

/* Takes a single line input from stdin and stores it in str. Returns str length. */
int getInputLine(char* str, int maxInput);

int main(int argc, char** argv) { ... }

int readlines(char* lineptr[], int maxLines) {
    /* Return number of lines read. */
    int numLines = 0;
    /* Buffer to store current line being read. */
    char currentLine[MAXINPUT];

    /* Terminate loop when enter is pressed at empty input or number of lines exceeds max. */
    while(getInputLine(currentLine,MAXINPUT) && numLines < maxLines) {
        /* Address of current line's first character is set to the appropriate index at lineptr. */
        lineptr[numLines] = currentLine;

        /* Both currentLine and lineptr[numLines] print accurately (note they are the same). */
        printf("CURRENT LINE:\t %s\n",currentLine);
        printf("lineptr[%d]:\t %s\n",numLines,lineptr[numLines]);

        numLines++;
    }

    /* ISSUE: Outside the loop, lineptr does NOT print anything. */
    printf("\nLOOPING\n");
    for(int i = 0; i < numLines; i++) {
        printf("%d: %s\n",i,lineptr[i]);
    }

    /* ISSUE: currentLine (which should be the last line entered) ALSO does not print outside the while. */
    printf("\ncurrentLine: %s",currentLine);

    return numLines;
}

我的问题是,在while()中,lineptrcurrentLine的内容会准确打印出来。但在while()之外,lineptrcurrentLine都不会打印任何内容。

当然,当我尝试将行读入char* []中的main()并尝试打印其内容时,此问题仍然存在。

为什么lineptr访问的地址中的内容是在循环内部打印而不是在外部打印?我错过了一些明显的东西吗?

2 个答案:

答案 0 :(得分:2)

那是因为您有一个名为currentLine的缓冲区,您可以在其中读取文本。然后,将currentLine的地址分配给lineptr[i],然后使用新文本覆盖其内容。因此,您的所有lineptr实际上都指向同一个位置,即currentLine的地址,currentLine仅包含您读取的最后一行。我想循环不打印任何东西,因为你读的最后一行是空的。

因此,为了使其工作,您需要在currentLine中读取一行,测量其长度,使用malloc()为该行分配足够的内存,从{{1}复制该行分配给内存,并将指针存储到currentLine中分配的内存中。

答案 1 :(得分:1)

这一行

    lineptr[numLines] = currentLine;

只需指定一个指向lineptr[numLines]的指针。这有几个问题:

  1. 每一行都指向同一个指针。
  2. 从函数返回后指针无效。
  3. 你需要使用类似于:

    的东西
        lineptr[numLines] = strdup(currentLine);
    

    请记住,strdup不是标准的C库函数。如果您的平台不支持它,您可以非常轻松地实现它。

    char* strdup(char const* in)
    {
        char* ret = malloc(strlen(in)+1);
        return strcpy(ret, in);
    }