0

你能告诉我为什么我没有从下面的函数中得到任何价值吗?

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

typedef struct {
    unsigned int length ;
    char * data ;
} String ;


String reverse(String this){

    String that;
    that=this;
    int i,j;
    j=that.length-1;
    char myc[that.length+1];

    for(i=0; i < that.length; i++, j--) {
         myc[i]=that.data[j];
    }
    myc[i+1]='\0';

    that.data= myc ;

    return that;
}
int main()
{
    String myStr;
    String myStrA;
    myStr.data= "This one is beautiful";
    myStr.length=21;

    String myStr2= reverse(myStr);

    printf("\n\nmy text before reverse :  %s \n", myStr.data);
    printf("\n\nmy text after reverse :  %s \n", myStr2.data);

    return 0;
}

// 反向函数应该返回一个反转的字符串,但它没有

4

2 回答 2

2

reverse

char myc[that.length+1];

for(i=0; i < that.length; i++, j--) {
     myc[i]=that.data[j];
}
myc[i+1]='\0';

that.data= myc ;   // <=== NO!!

您正在为您的返回值分配一个本地 VLA,从而隐藏了如果您直接返回数组,您会得到的“返回本地数组”警告(运气不好)。

因此,一旦函数返回,您就会丢失该值,因为它超出了范围,并且内存被程序重用(未定义的行为)。

因此,您应该复制数据,以便全局分配内存that.data = strdup(myc)

甚至更好:不要创建 VLA 而是直接分配,这样可以保存副本,您myc现在可以安全地分配:

char *myc = malloc(that.length+1);

(并在不再需要时释放它)

于 2017-12-18T15:56:19.527 回答
-4

代码不好,我认为问题在于您使用 g++ 进行编译,因为您有“this”关键字。使用 GCC 编译,然后“this”将不是关键字而是标识符。C++ 是 OOP,这就是为什么“this”是关键字的原因。

然而,其他评论提到了一个问题,那就是“this.data=myc”。数组“myc”是在作用域而不是堆上声明的,因此它具有未定义的行为,并且在堆栈更改时可能指向完全不同的东西。而是在堆上或在全局范围内创建数组。

于 2017-12-18T15:58:16.093 回答