在解析相同的参数时,有时会出现段错误
While parsing same arguments, sometimes segfault
我正在编写一个 C++ 程序,它将从两个单独的文件中读取两个矩阵。它最终会处理这些矩阵,但我现在在解析命令行选项时遇到问题。这就是向我展示数据的方式。
有几个不同的命令行变体:
dtype N file1 file2 file3
dtype N M L file1 file2 file3
其中 dtype 可以是 int 或 double,如果只提供 N,则所有矩阵都是 NxN,否则矩阵 1 是 NxM,矩阵 2 如果是 MxL,文件 1 和 2 包含要操作的矩阵,而文件 3 是结果所在的位置将被存储。
我已经将到目前为止所写的内容包含在下面。我是 C++ 的新手,所以请不要对您的批评太苛刻。
现在的问题是,如果我 运行 这段代码似乎完全 运行dom 如果它会出现段错误,我不知道是什么导致了它。我知道解决段错误可能会很痛苦,我在这里查看其他问题,但我别无选择,只能寻求您的帮助,因为我处于停滞状态。
为了排除故障,我使用 -g 选项编译了 g++,运行 我的程序是通过 gdb 编译的。我无法通过 gdb 复制段错误。
#include <iostream>
#include <string>
#include <string.h>
#include <vector>
#include <fstream>
#include <typeinfo>
#include <sys/stat.h>
#include <stdexcept>
using namespace std;
inline bool exists_test(const std::string& name) {
struct stat buffer;
return (stat (name.c_str(), &buffer) == 0);
}
int main(int argc, char const *argv[])
{
int dtype = 0; // 0 = int; 1 = double
int M = 0;
int N = 0;
int L = 0;
const char *file1;
const char *file2;
const char *file3;
for (int i=1; i<argc ; i++)
{
try
{
if(i==1){
if(!((strcmp(argv[1], "int") == 0) || (strcmp(argv[1], "double") == 0))){
throw invalid_argument("wrong dtype");
}else{
if((strcmp(argv[1], "double") == 0)){
dtype = 1;
}
}
}else if(i==2){
M=stoi(argv[i]);
}else if(i==3){
if(!exists_test(argv[i])){
N=stoi(argv[i]);
}else{
file1 = argv[i];
}
}else if(i==4){
if(!exists_test(argv[i])){
L=stoi(argv[i]);
}else{
file2 = argv[i];
}
}else if(i==5 || i==6 || i==7){
if(!exists_test(argv[i])){
throw invalid_argument("no such file");
}else{
if(i==6){
file2 = argv[i];
}else if(i==7){
file3 = argv[i];
}else if(strcmp(file1, argv[i]) == 0){
}else{
file1 = argv[i];
}
}
}
continue;
}
catch (...)
{
cout << "error code 1 or this one" << endl;
return 1;
}
}
if(N==0){
N=M;
}
if(L==0){
L=M;
}
ifstream thisfile;
double filler = 0;
vector<double> readThese;
vector< vector<double> > matrixA(4, vector<double>(3, 0));
thisfile.open(file1);
while (thisfile >> filler )
{
readThese.push_back(filler);
}
thisfile.close();
//for(int j = 0; j < N; j++){
// matrixA[0][j] = readThese[j];
//}
cout << matrixA[0][0] << " " << matrixA[0][1] << " " << matrixA[0][2] << " " << matrixA[0][3] << endl;
cout << matrixA[1][0] << " " << matrixA[1][1] << " " << matrixA[1][2] << " " << matrixA[1][3] << endl;
cout << matrixA[2][0] << " " << matrixA[2][1] << " " << matrixA[2][2] << " " << matrixA[2][3] << endl;
cout << matrixA[3][0] << " " << matrixA[3][1] << " " << matrixA[3][2] << " " << matrixA[3][3] << endl;
}
下面显示了程序的输出。也不是每次都出segfault,只是这次才出。
$ ./a.out int 3 4 1 file1 file2
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 5.14322e-321
$ ./a.out int 3 4 1 file1 file2
Segmentation fault (core dumped)
$ ./a.out int 3 4 1 file1 file2
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 5.14322e-321
$ ./a.out int 3 4 1 file1 file2
Segmentation fault (core dumped)
您声明
matrixA(4, vector<double>(3, 0));
表示一个 4 x 3 矩阵,但随后访问第 4 列
cout << matrixA[0][0] << " " << matrixA[0][1] << " "\
<< matrixA[0][2] << " " << matrixA[0][3] << endl;
^^^^^^^^^^^^^
here
这是不存在的,所以你会遇到段错误。越界测试,越界访问可以使用std::vector::at()
instead of std::vector::operator[]
, it is slower but throws an std::out_of_range
异常。一旦你确定代码没问题,你就可以反转到operator[]
。
顺便说一句,通常将矩阵表示为 vector<vector>
是个坏主意。最好使用单个向量并将 1D 坐标映射到 2D 坐标,反之亦然,因为单个向量保证元素连续存储在内存中,因此您具有更好的缓存局部性。
我正在编写一个 C++ 程序,它将从两个单独的文件中读取两个矩阵。它最终会处理这些矩阵,但我现在在解析命令行选项时遇到问题。这就是向我展示数据的方式。
有几个不同的命令行变体:
dtype N file1 file2 file3
dtype N M L file1 file2 file3
其中 dtype 可以是 int 或 double,如果只提供 N,则所有矩阵都是 NxN,否则矩阵 1 是 NxM,矩阵 2 如果是 MxL,文件 1 和 2 包含要操作的矩阵,而文件 3 是结果所在的位置将被存储。
我已经将到目前为止所写的内容包含在下面。我是 C++ 的新手,所以请不要对您的批评太苛刻。
现在的问题是,如果我 运行 这段代码似乎完全 运行dom 如果它会出现段错误,我不知道是什么导致了它。我知道解决段错误可能会很痛苦,我在这里查看其他问题,但我别无选择,只能寻求您的帮助,因为我处于停滞状态。
为了排除故障,我使用 -g 选项编译了 g++,运行 我的程序是通过 gdb 编译的。我无法通过 gdb 复制段错误。
#include <iostream>
#include <string>
#include <string.h>
#include <vector>
#include <fstream>
#include <typeinfo>
#include <sys/stat.h>
#include <stdexcept>
using namespace std;
inline bool exists_test(const std::string& name) {
struct stat buffer;
return (stat (name.c_str(), &buffer) == 0);
}
int main(int argc, char const *argv[])
{
int dtype = 0; // 0 = int; 1 = double
int M = 0;
int N = 0;
int L = 0;
const char *file1;
const char *file2;
const char *file3;
for (int i=1; i<argc ; i++)
{
try
{
if(i==1){
if(!((strcmp(argv[1], "int") == 0) || (strcmp(argv[1], "double") == 0))){
throw invalid_argument("wrong dtype");
}else{
if((strcmp(argv[1], "double") == 0)){
dtype = 1;
}
}
}else if(i==2){
M=stoi(argv[i]);
}else if(i==3){
if(!exists_test(argv[i])){
N=stoi(argv[i]);
}else{
file1 = argv[i];
}
}else if(i==4){
if(!exists_test(argv[i])){
L=stoi(argv[i]);
}else{
file2 = argv[i];
}
}else if(i==5 || i==6 || i==7){
if(!exists_test(argv[i])){
throw invalid_argument("no such file");
}else{
if(i==6){
file2 = argv[i];
}else if(i==7){
file3 = argv[i];
}else if(strcmp(file1, argv[i]) == 0){
}else{
file1 = argv[i];
}
}
}
continue;
}
catch (...)
{
cout << "error code 1 or this one" << endl;
return 1;
}
}
if(N==0){
N=M;
}
if(L==0){
L=M;
}
ifstream thisfile;
double filler = 0;
vector<double> readThese;
vector< vector<double> > matrixA(4, vector<double>(3, 0));
thisfile.open(file1);
while (thisfile >> filler )
{
readThese.push_back(filler);
}
thisfile.close();
//for(int j = 0; j < N; j++){
// matrixA[0][j] = readThese[j];
//}
cout << matrixA[0][0] << " " << matrixA[0][1] << " " << matrixA[0][2] << " " << matrixA[0][3] << endl;
cout << matrixA[1][0] << " " << matrixA[1][1] << " " << matrixA[1][2] << " " << matrixA[1][3] << endl;
cout << matrixA[2][0] << " " << matrixA[2][1] << " " << matrixA[2][2] << " " << matrixA[2][3] << endl;
cout << matrixA[3][0] << " " << matrixA[3][1] << " " << matrixA[3][2] << " " << matrixA[3][3] << endl;
}
下面显示了程序的输出。也不是每次都出segfault,只是这次才出。
$ ./a.out int 3 4 1 file1 file2
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 5.14322e-321
$ ./a.out int 3 4 1 file1 file2
Segmentation fault (core dumped)
$ ./a.out int 3 4 1 file1 file2
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 1.63042e-322
0 0 0 5.14322e-321
$ ./a.out int 3 4 1 file1 file2
Segmentation fault (core dumped)
您声明
matrixA(4, vector<double>(3, 0));
表示一个 4 x 3 矩阵,但随后访问第 4 列
cout << matrixA[0][0] << " " << matrixA[0][1] << " "\
<< matrixA[0][2] << " " << matrixA[0][3] << endl;
^^^^^^^^^^^^^
here
这是不存在的,所以你会遇到段错误。越界测试,越界访问可以使用std::vector::at()
instead of std::vector::operator[]
, it is slower but throws an std::out_of_range
异常。一旦你确定代码没问题,你就可以反转到operator[]
。
顺便说一句,通常将矩阵表示为 vector<vector>
是个坏主意。最好使用单个向量并将 1D 坐标映射到 2D 坐标,反之亦然,因为单个向量保证元素连续存储在内存中,因此您具有更好的缓存局部性。