簡體   English   中英

與main.cpp以外的文件中定義的結構的奇怪性

[英]Oddity with structs defined in files other than main.cpp

我發現在一個單獨的Cpp文件中定義了一個結構(帶有一個雙精度數組和一個整數數組),但是從main調用的結果將不合理的值發送給cout用於數組。 下面我希望是最小的例子,以及控制台輸出。

我的道歉應該是我的代碼被擾亂 - 我一直在努力格式化它。

如果有人能幫助我理解並糾正這一點,我將不勝感激。

最好,喬

(1)main.cpp:

#include "iostream"
#include "defs.h"

using namespace std;

int main()
{
    MyStruct myModel=ConstructModel();

    cout << endl << "myModel goes first:" << endl;
    for(int i=0; i<myModel.n; i++)
        cout << "myModel.Y[" << i << "]=" << myModel.Y[i] << endl;
    cout << "myModel.n=" << myModel.n << endl;

    MyStruct myOtherModel;
    myOtherModel.n=2; double Y[2]={0.1,0.1};
    myOtherModel.Y=Y;

    cout << endl << "now myOtherModel:" << endl;
    for(int i=0; i<myModel.n; i++)
        cout << "myOtherModel.Y[" << i << "]=" << myOtherModel.Y[i] << endl;

    return 0;
}

(2)defs.cpp:

#include "defs.h"

MyStruct ConstructModel()
{
 MyStruct Model;

 double Y[2]={0.1,0.1}; Model.Y=Y;
    int n=2; Model.n=n;

    return Model;
}

(3)defs.h:

#ifndef DEFS_H  
#define DEFS_H

struct MyStruct
{
    double *Y;//length (n+1)
    int n;
};

MyStruct ConstructModel();

#endif

控制台輸出

在我的機器上(WinXP 32bit,MSVC2008),這給出了:

myModel排在第一位:

myModel.Y [0] = 1.12947e-307

myModel.Y [1] = 1.80243e-307

myModel.n = 2

現在myOtherModel:

myOtherModel.Y [0] = 0.1

myOtherModel.Y [1] = 0.1

你的struct包含一個指向雙精度的裸指針。 在defs.cpp中,您將其初始化為局部變量。 ConstructModel()范圍之外,該內存不再有效。

如果你想在一個struct中使用一個數組,你必須聲明它(包括它的大小,然后必須對所有MyStruct都相同)。 但是,為什么不使用例如std::list<double>std::vector<double>

的問題是,在陣列Y包含在ConstructModel僅適用於只要ConstructModel正在執行。 您(間接)傳回一個指向此局部變量的指針,該局部變量在被訪問時不再有效。

MyStruct ConstructModel()
{
  MyStruct Model;

  double Y[2]={0.1,0.1}; 

在這里你將本地Y[0]的地址分配給Model.Y

  Model.Y=Y;
  int n=2; 
  Model.n=n;

  return Model;

這里局部Y超出范圍並被銷毀,使Model.Y具有指向不存在對象的指針:

}

當ConstructModel函數完成時,數組超出范圍。 嘗試在堆上創建數組。

這不是答案,而是上面的另一個問題。

如果我將代碼更改為如下所示,當結構只包含這一個指針時,指針似乎不會超出范圍。 如果結構被定義為包含另一個值(例如,整數),則地址將丟失。 難道這似乎沒有表明對我的第一個問題的解釋不完整嗎?

我不確定這對任何人是否有任何興趣。 我懷疑聲明和定義/分配結構的內部導致這種現象 - 也許有人可以確認/解釋。

#include "iostream"
using namespace std;

struct MyStruct
{
    //int n; // <-- if commented, result is as expected. Else, address is lost.
    double *Y;//length (n+1)
};

MyStruct ConstructModel()
{
    MyStruct Model;
    //int n=2; Model.n=n;
    double Y[2]={0.1,0.1}; Model.Y=Y;
    return Model;
}


int main()
{
    MyStruct myModel=ConstructModel();

    for(int i=0; i<2; i++)
        cout << "myModel.Y[" << i << "]=" << myModel.Y[i] << endl;

    return 0;
}

更新:使用g ++而不是MSVC進行編譯不會顯示輸出的差異。 因此似乎是編譯器特定的......

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM