2016-01-29 53 views
-5

我是C++的新手,我有一個問題(抱歉,如果它是基本的東西,但我想知道)。所以我有這個代碼是應該一個向量的每個元素乘以一個數字:C++中的向量分段錯誤

#include<iostream> 
#include "IntCell.h" 
#include<vector> 
using namespace std; 

vector<float> MatMult(int a, vector<float> & b) 
{ 
vector<float> c; 
int i; 
for(i=0;i<=b.size();i++){ 
    c[i]=b[i]*a; 
} 
return c; 

} 

int main() 


{int a=3; 
vector<float> b{1,2,3,4,5}; 
vector<float> c = MatMult(a,b); 
cout<<c[2]; 
} 

它編譯罰款,但我得到段錯誤:11.什麼是錯的呢? 謝謝!

+1

你應該重複** **之前b.size(),因爲向量0索引 – Incomputable

+0

檢查線在'for',你要計算是不是你真的想計算一下。 – tkausl

+0

你從未初始化過'c'。 – NathanOliver

回答

2

vector<float> c;創建一個空向量。您然後在c[i]=b[i]*a;中使用它,這是未定義的行爲,因爲c[anything]不存在。

如果您想使用c[i]=b[i]*a;,您需要使cb尺寸相同。這將是這樣的:

vector<float> MatMult(int a, vector<float> & b) 
{ 
    vector<float> c(b.size()); 

    for(int i = 0; i < b.size(); i++){ 
//     ^use < here since b[b.size()] is out of bounds 
     c[i]=b[i]*a; 
    } 

    return c; 
} 
+0

謝謝。就是這樣。 – SSSJ

+0

@SSSJ沒問題 – NathanOliver

2

你不能只做c[i],因爲目前還沒有這樣的索引。你最好寫c.push_back(b[i] * a)或預先分配內存c.reserve(b.size())

更重要的是,b.size()返回元素的數量在一個載體,而不是最大指數,所以你應該使用i < b.size(),而不是i <= b.size()

+1

他/她正在做我<= b.size()-1,非常規但沒有錯誤 – ForeverStudent

+2

@ForceBru:在你的防守中,問題首先沒有'-1'。 –

+1

@LightnessRacesinOrbit,當討厭者以這種暴力的方式改變他們的問題時,我討厭它。把它捲起來。 – ForceBru

1

除了其他的答案給出,發現馬上一個方式,如果你正在訪問向量出界是首先開發使用vector::at(),而不是使用[]

vector<float> MatMult(int a, vector<float> & b) 
{ 
    vector<float> c; 
    int i; 
    for(i=0;i<=b.size();i++){ 
     c.at(i) = b.at(i) * a; 
} 
return c; 

而是分段錯誤,你會被給予out_of_range異常,從而給你的問題是什麼更多的信息。一旦你擺脫了所有的out_of_range錯誤,你可以切換到使用[]

Live Example using vector::at

+0

@NathanOliver:No. –

+0

@LightnessRacesinOrbit當然是啊。異常彈出窗口仍然有異常類型。 – NathanOliver

+0

@NathanOliver:我不知道什麼是「異常彈出」,但是如果你不處理這個異常,那麼你的程序將被終止,任何值得它的salt的調試器都可以用來確定它是什麼異常舉起等 –

3

如果你有一個較新的編譯器,這是簡單的。按值取vector,並使用基於範圍的for循環以避免超出範圍的錯誤。

vector<float> MatMult(int a, vector<float> b) 
{ 
    for (float& value : b) { 
     value *= a; 
    } 
    return b; 
} 

這可以作爲模板函數更通用。注意下面的代碼幾乎肯定可以改進。

template <typename T> 
vector<T> MatMult(int a, vector<T> b) 
{ 
    for (auto& value : b) { 
     value *= a; 
    } 
    return b; 
} 
+0

爲什麼''''自動'爲了使它更容易在將來改變? – NathanOliver

+0

@NathanOliver:我可能把它作爲模板,然後使用'auto'。 – Blastfurnace

+0

@NathanOliver:如果'b'發生了變化,那麼你的函數在語義上已經發生了變化,因此你可能希望被迫記住重新讀取函數以確保沒有其他東西需要改變。 'auto'阻止編譯器執行這些最基本的編譯器活動。循環被設計爲在'float'上運行,所以寫'float'! –