2013-11-09 42 views
1

我的代碼編譯得很好。但是,當我嘗試使用我的重載運算符< < - 應用程序崩潰。我沒有自己找到任何決定。如果我不使用這個操作符,一切正常。例如,我可以將負面的參數傳遞給構造函數,它會使用類數據指針'company'顯示一條消息。調試器顯示PROGRAMM崩潰這一行:分割錯誤過載運算符<<

os << "Company: " << s.company 

在功能:

std::ostream& operator<<(std::ostream& os, const Stock& s) 
{ 
using std::ios_base; 
// set format to #.### 
ios_base::fmtflags orig = 
    os.setf(ios_base::fixed, ios_base::floatfield); 
std::streamsize prec = os.precision(3); 

os << "Company: " << s.company 
    << " Shares: " << s.shares << '\n'; 
os << " Share Price: $" << s.share_val; 
// set format to #.## 
os.precision(2); 
os << " Total Worth: $" << s.total_val << '\n'; 

// restore original format 
os.setf(orig, ios_base::floatfield); 
os.precision(prec); 
return os; 
} 

下面的代碼:

// stock20.h -- augmented version 
#ifndef STOCK20_H_ 
#define STOCK20_H_ 
#include <iostream> 
class Stock 
{ 
private: 
char* company; 
int shares; 
double share_val; 
double total_val; 
void set_tot() { total_val = shares * share_val; } 
public: 
Stock();  // default constructor 
Stock(const char* co, long n = 0, double pr = 0.0); 
~Stock();  // do-nothing destructor 
void buy(long num, double price); 
void sell(long num, double price); 
void update(double price); 
const Stock & topval(const Stock & s) const; 
friend std::ostream& operator<<(std::ostream& os, const Stock& s); 
}; 

#endif 

實現:

// stock20.cpp -- augmented version 
#include "stock20.h" 
#include <cstring> 

#define my_delete(x){ delete[] x; x = NULL; } 
using namespace std; 
// constructors 
Stock::Stock()  // default constructor 
{ 
company = new char[1]; 
company[0] = '\0'; 
shares = 0; 
share_val = 0.0; 
total_val = 0.0; 
} 

Stock::Stock(const char* co, long n, double pr) 
{ 
    company = new char[strlen(co)+1]; 
    strcpy(company,co); 

if (n < 0) 
{ 
    std::cout << "Number of shares can't be negative; " 
       << company << " shares set to 0.\n"; 
    shares = 0; 
} 
else 
    shares = n; 
share_val = pr; 
set_tot(); 
} 

// class destructor 
Stock::~Stock()  // quiet class destructor 
{ 
    my_delete(company); 
} 

// other methods 
void Stock::buy(long num, double price) 
{ 
if (num < 0) 
{ 
    std::cout << "Number of shares purchased can't be negative. " 
     << "Transaction is aborted.\n"; 
} 
else 
{ 
    shares += num; 
    share_val = price; 
    set_tot(); 
} 
} 

void Stock::sell(long num, double price) 
{ 
using std::cout; 
if (num < 0) 
{ 
    cout << "Number of shares sold can't be negative. " 
     << "Transaction is aborted.\n"; 
} 
else if (num > shares) 
{ 
    cout << "You can't sell more than you have! " 
     << "Transaction is aborted.\n"; 
} 
else 
{ 
    shares -= num; 
    share_val = price; 
    set_tot(); 
} 
} 

void Stock::update(double price) 
{ 
share_val = price; 
set_tot(); 
} 

std::ostream& operator<<(std::ostream& os, const Stock& s) 
{ 
using std::ios_base; 
// set format to #.### 
ios_base::fmtflags orig = 
    os.setf(ios_base::fixed, ios_base::floatfield); 
std::streamsize prec = os.precision(3); 

os << "Company: " << s.company 
    << " Shares: " << s.shares << '\n'; 
os << " Share Price: $" << s.share_val; 
// set format to #.## 
os.precision(2); 
os << " Total Worth: $" << s.total_val << '\n'; 

// restore original format 
os.setf(orig, ios_base::floatfield); 
os.precision(prec); 
return os; 
} 

const Stock & Stock::topval(const Stock & s) const 
{ 
if (s.total_val > total_val) 
    return s; 
else 
    return *this; 
} 

和代碼的使用:

// usestok2.cpp -- using the Stock class 
// compile with stock20.cpp 
#include "stock20.h" 

const int STKS = 4; 
int main() 
{{ 
//create an array of initialized objects 
    Stock stocks[STKS] = { 
    Stock("NanoSmart", 12, 20.0), 
    Stock("Boffo Objects", 200, 2.0), 
    Stock("Monolithic Obelisks", 130, 3.25), 
    Stock("Fleep Enterprises", 60, 6.5) 
    }; 

std::cout << "Stock holdings:\n"; 
int st; 
for (st = 0; st < STKS; st++) 
    std::cout<<stocks[STKS]; //here we got an error 
// set pointer to first element 
const Stock * top = &stocks[0]; 
for (st = 1; st < STKS; st++) 
    top = &top->topval(stocks[st]); 
// now top points to the most valuable holding 
std::cout << "\nMost valuable holding:\n"; 
std::cout<<*top;} 
// std::cin.get(); 
return 0; 
} 

如果因爲我問了1個問題,我希望你不介意我問另一個問題。我如何避免使用包含在標題中。例如,對於重載運算符< <我需要包含iostream,因爲它具有返回值類型ostream &和相同類型的參數。提前致謝。

+0

不確定你爲什麼要避免在頭文件中使用'#include'。這是一種正常的做法。 – godel9

+0

我不知道,我在某個地方發紅,說這是不對的,最好避免這種做法。所以沒關係,如果我在我的頭文件中包含iostream,然後將iostream包含在使用頭文件的代碼中?這不會有什麼不好? –

+0

請參閱[這個問題]的答案(http://stackoverflow.com/questions/2596449/including-includes-in-header-file-vs-source-file)以獲得比我可以融入評論更好的解釋。 :-) – godel9

回答

3

當聲明的數組:

Stock stocks[STKS] = ... 

陣列元件通過STKS - 1索引0。當你在這一行訪問stocks[STKS]

std::cout<<stocks[STKS]; // Out-of-bounds: STKS > STKS - 1 

你訪問一個不存在的數組元素,這是造成死機。鑑於上下文,您可能需要std::cout<<stocks[st];(帽子提示:@ gx_)。

+0

哦,我真是個笨蛋。一遍又一遍地看着代碼,沒有注意到那個簡單的錯誤....非常感謝你! –

+0

@FuzzyToozy不客氣。既然你是新來的,請不要忘記,以紀念接受了答案,幫助最解決問題。另請參閱[如何接受答案工作](http://meta.stackexchange.com/questions/5234/how-does-accepting-an-answer-work)? – godel9