繁体   English   中英

C 分配 memory 错误。 找不到这样的东西

[英]C allocation memory error. Don't find something like this

你能帮忙吗? 当我执行此代码时,我收到: AAAAABBBBBCCCCCBBBBBCOMP¬ıd┐╔ LENGTH 31 字母后面有一些奇怪的字符,而我只分配了 21 个字节。

#include <stdio.h>
#include <stdlib.h>
char * lineDown(){
    unsigned short state[4] = {0,1,2,1};
    char decorationUp[3][5] = {
        {"AAAAA"},{"BBBBB"},{"CCCCC"}
    };
    char * deco = malloc(21);
    int k;
    int p = 0;
    for(int j = 0; j < 4; j++){
        k = state[j];
        for(int i = 0; i < 5; i++){
           *(deco+p) = decorationUp[k][i];
           p++;
        }
    }
    return deco;
}
int main(void){

    char * lineDOWN = lineDown();
    int k = 0;
    char c;
    do{
        c = *(lineDOWN+k);
        printf("%c",*(lineDOWN+k));
        k++;
    }while(c != '\0');
    printf("LENGTH %d\n\n",k);
}

function 不构建字符串,因为结果数组不包含终止零,尽管在分配数组时为其保留了空间。

char * deco = malloc(21);

因此,在退出 function 之前,您需要 append 终止零的数组

    //... 
    *(deco + p ) = '\0';

    return deco;
}

否则这个do-while循环

do{
    c = *(lineDOWN+k);
    printf("%c",*(lineDOWN+k));
    k++;
}while(c != '\0')

将有未定义的行为。

但是,即使您将 append 与终止零的数组循环将不正确地计算存储字符串的长度,因为即使当前字符是终止零,它也会增加变量 k 。

相反,您应该使用 while 循环。 在这种情况下,变量c的声明将是多余的。 循环看起来像

while ( *( lineDOWN + k ) )
{
    printf("%c",*(lineDOWN+k));
    k++;
}

在这种情况下,此调用

printf("\nLENGTH %d\n\n",k);
        ^^

将 output 字符串的正确长度等于20

并且您应该在退出程序之前释放分配的 memory

free( lineDOWN );

正如其他一些人在他们的回答中所写的那样,数组decorationUp必须声明为

char decorationUp[3][6] = {
    {"AAAAA"},{"BBBBB"},{"CCCCC"}
};

那么如果您不打算将数组的元素用作字符串并且不将它们用作程序中的字符串,则没有必要。

考虑到您的程序充满了幻数。 这样的程序通常容易出错。 相反,您应该使用命名常量。

char decorationUp[3][5] = {
    {"AAAAA"},{"BBBBB"},{"CCCCC"}
};

您的字符串还需要 6 个字符才能放置 null 字符,即使在这种情况下,您也不会将它们用作“标准”字符串,而仅将它们用作字符数组。 为了养成习惯,总是反转结束 null 字符的位置

你可以做

char decorationUp[3][6] = {
    {"AAAAA"},{"BBBBB"},{"CCCCC"}
};

注意给出第一个大小是没有用的,编译器会为你计算

因为在main中,当您读取 null 字符时您会停止,您还需要将它放在最后的deco中,因此您需要为其分配 21。 和以前一样,您错过了 null 字符的位置,但这里会产生未定义的行为,因为您在分配的块之后读取。

*(deco+p)不可读,做deco[p]

例如:

char * lineDown(){
    unsigned short state[] = {0,1,2,1};
    char decorationUp[][6] = {
        {"AAAAA"},{"BBBBB"},{"CCCCC"}
    };
    char * deco = malloc(4*5 + 1); /* a formula to explain why 21 is better than 21 directly */
    int k;
    int p = 0;
    for(int j = 0; j < 4; j++){
        k = state[j];
        for(int i = 0; i < 5; i++){
           deco[p] = decorationUp[k][i];
           p++;
        }
    }
    deco[p] = 0;
    return deco;
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM