通过引用传递修改数组后,为什么它保持不变?

时间:2014-10-26 05:37:34

标签: c++ arrays pointers stack dynamic-arrays

我正在通过创建一个Big Number结构来练习指针,该结构具有numDigits(位数)和数字(大数字的内容)。

我创建了一个名为removeZero()的函数。在将整数数组和大小n传递给它之后,由于通过引用传递,我应该减少输入的前导零。当整数数组在main函数中时,它可以工作。但是,当我传递一个readDigits中的数组时,它不返回非前导零版本。为什么?怎么解决?

struct BigNum{
    int numDigits;
    int *digits;  //the content of the big num
};

int main(){
    int A[] = {0,0,0,0,0,0,1,2,3};
    int n=9;
    int *B=A;
    //removeZero(A,n); If I use this, it cannot compile
    //error: invalid initialization of non-const reference of type ‘int*&’ from an rvalue of type ‘int*’

    removeZero(B,n);
    for (int i=0; i<n; i++){
    std::cout << *(B+i) << std::endl;
    }

    BigNum *num = readDigits();

    return 0;
}

BigNum* readDigits(){  
    std::string digits;
    std::cout << "Input a big number:" << std::endl;
    std::cin >> digits; 

    //resultPt in heap or in stack?
    int *resultPt = new int[digits.length()]; //in heap
    int n = digits.length();
    toInt(digits,resultPt);
    removeZero(resultPt,n);

    //Output the leading zeros, why?
    for (int i=0; i<n; i++){
    std::cout << *(resultPt +i) << std::endl;
    }

    BigNum *numPtr = new BigNum();
    numPtr->numDigits = n;
    numPtr->digits = resultPt;

    return numPtr;
}

void toInt(std::string& str, int *result){
    for (int i=0;i<str.length() ;i++ ){
    result[str.length()-i-1] = (int)(str[i]-'0');
    }
}

void removeZero(int* &A,int& n){
    int i=0;
    while (A[i]==0){
    i++;
    }
    A=A+i; //memory leak?
    n=n-i;
}

bool areDigits(std::string num){
    for(int i=0;i<num.length();i++){
    if(num[i]<'0' || num[i] >'9'){
        return false;
     }
    }
    return true;
}

5 个答案:

答案 0 :(得分:0)

可能是numPtr.numPtr范围的问题是函数readDigits()的局部变量。而不是返回指针。将num传递给readDigits()。

答案 1 :(得分:0)

您的removeZero功能的签名是:

void removeZero(int* &A,int& n);

这意味着forst参数是指针的引用,但指针是非const指针,因此您不能在那里传递数组,因为数组是常量指针(起始地址不能更改)。 实际上,您正在更改removeZero中的起始地址。 使用removeZero,可以从以下位置更改while循环:

while (A[i]==0){

为:

while ((A[i]==0) && (i<n)){

答案 2 :(得分:0)

请注意,数组和指针是两个不同的东西。将数组传递给函数时,它会降级为const指针。这意味着您无法将数组传递给期望int*&

的函数

答案 3 :(得分:0)

toInt中存在逻辑错误。

void toInt(std::string& str, int *result){
    for (int i=0;i<str.length() ;i++ ){

    // This stores the digits in the reverse order.
    result[str.length()-i-1] = (int)(str[i]-'0');
    }
}

该行应为

    result[i] = (int)(str[i]-'0');

如果您打算以相反的顺序保留数字,则必须更改removeZero,并牢记这一点。 `

答案 4 :(得分:0)

当你说

int *B=A;

你只是创建一个指向同一内存的指针 数组A.仅通过递增函数内的指针(* B) removeZero

A=A+i;

你没有删除任何东西,只是你只是递增指针(* B) 指向数组中的后续内存位置。 由于你,A指向的原始数组内存保持不变 没有改变阵列的任何内容,但你有 递增指针指向与数组相同的内存位置。

还有很多问题,例如&#34; Debasish Jana&#34;提及, 你必须改变你的while循环。 &#34;&#34;代码学徒&#34;给了你理由 取消注释注释代码时出现编译错误。 也在&#34; removeZero&#34;你用A而不是&#34; 1&#34;来增加A像

A=A+1;

这是您遇到奇怪行为的原因之一

即使更改了所有这些,您也看不到您的阵列发生了变化, 因为你没有修改数组的任何内容。

如果您确实要删除数组的内容并动态更改它, 你必须去Vector&lt;&gt ;.使用静态内存分配你无法削减 通过在这里和那里删除一些元素来缩短数组大小。学习矢量&lt;&gt;!