"if (argc < 2 || argc > 2)" 应该有 2 个参数吗? & 在抛出 'std::out_of_range' 错误实例后调用终止
Should "if (argc < 2 || argc > 2)" be fine with 2 arguments? & terminate called after throwing an instance of 'std::out_of_range' error
解决方法:使用if (argc !=3)
和getline(row_as_stringstream, substr, ';')
这是我之前问题的延续:,它允许代码编译没有任何错误
我是 C++ 的新手,我正在尝试从我的主管那里调试这段代码。
原始代码以csv
文件作为输入,包含integers
的行和列
和 strings
。现在我们正在读取一个 txt
文件,其形状为:
TEXT
0; INT; INT; INT; INT; ...
0; INT; INT; INT; INT; ...
18 more lines of the above numbers and semicolons
在那个文件中,我在一个实例中用换行符替换了分号,在另一个实例中用空格替换了分号,因为我不确定我们需要哪个。
解决方法:使用带分号的txt
文件,但去掉行尾的分号.
if (argc < 2 || argc > 2)
似乎有问题。它抛出“用法:./a.o <> <>”错误消息。但是,两者都是严格不等式。这个 if
不应该有 2 个参数吗?在原始代码中,它显示为 if (argc < 2 || argc > 3)
,我将其改回。
编辑: 由于 john 也指出了 "program name is an argument",所以我实际上想要 3 而不是 2.
两个 txt
文件(换行符和空格)似乎在下面产生相同的错误消息
错误信息:(对于int
阈值我尝试了各种值)
Registering only edges shorter than int.
terminate called after throwing an instance of 'std::out_of_range'
what(): vector::_M_range_check: __n (which is 1) >= this->size() (which is 1)
Aborted (core dumped)
想法:
当我们有一个简单的案例时,我知道此错误消息的含义,对于 example:
#include <vector>
int main()
{
std::vector<int> v;
v.push_back(123); // v has 1 element [0 to 0]
int x4 = v.at(3); // exception
}
我们得到一个异常,因为 v 有 1 个元素,而元素 3 不存在。
但是,在我的代码中,我不确定要查找的内容。
原始代码读取了带有行和列的 csv
,但在这种情况下,中间有空格的矩阵形式可能会导致问题。这是否意味着我只想要一个看起来像列向量的 txt
文件?那是我试过的一个文件,所以代码可能对列数不满意?
相关函数:
int main(int argc, char** threshold_and_distanceMatrixfilename)
{
if (argc < 2 || argc > 3)
{
std::cerr << "Usage: ./distanceMatrixToSageGraph.o <threshold>
<distanceMatrix_file_calculated_fromDGEsingleCell_data>" << std::endl;
return -1;
}
string distanceMatrixfilename = threshold_and_distanceMatrixfilename[2];
int threshold = std::stoi(threshold_and_distanceMatrixfilename[1]);
std::ifstream distanceMatrixFile(distanceMatrixfilename);
if (!distanceMatrixFile)
{
std::cerr << "Error opening distanceMatrix file: " << distanceMatrixfilename << std::endl;
return -1;
}
string row;
std::getline(distanceMatrixFile, row); // discard the first row, which specifies the format of the file.
vector<vector<int>> the_entries;
while (std::getline(distanceMatrixFile, row))
{
std::stringstream row_as_stringstream(row);
int i; i = 0;
vector<string> row_as_vector;
while (row_as_stringstream.good())
{
string substr;
getline(row_as_stringstream, substr, ',');
row_as_vector.push_back( std::stoi(substr) );
};
the_entries.push_back(row_as_vector); //LINE 104
};
}
整个代码:
// Convert distanceMatrix tables of protein interactions to SAGE graph.
///////////////////////////////////////////////////////////////////////////
#include <iostream>
#include <fstream>
#include <sstream>
#include <math.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <list>
#include <vector>
#include <tuple>
#include <algorithm>
using namespace std;
void writeGraphInSageFormat(string name, std::vector<std::vector<int>> TheEdges)
{
//////////////////////////////////////////////////////////////////////////////////////
// Write out the edges in SAGE format.
///////////////////////////////////////////////////////////////////////////////////////
int edgeNumber = TheEdges.size();
ofstream d1sageFile(name, ios::out);
d1sageFile << "g = Graph([" << endl;
for (int n = 0; n < edgeNumber; n++) {
d1sageFile << "(" << TheEdges[n][0] + 1 << "," << TheEdges[n][1] + 1 << ")," << endl;
}
d1sageFile << "])" << endl;
d1sageFile << "g.show()" << endl;
d1sageFile.close();
std::cout << "SAGE graph written into the file " << name << std::endl;
}
std::vector<std::vector<int>> ConvertEntriesMatrixToEdges(vector<vector<int>> the_entries, int threshold)
{
////////////////////////////////////////////////////////////////////////////////////////////
// Construct the edge-vertex incidence matrix (d_1) from the distanceMatrix entries matrix:
////////////////////////////////////////////////////////////////////////////////////////////
std::vector<std::string> proteinNames;
std::vector<std::vector<int>> TheEdges;
std::cout << "Registering only edges shorter than " << threshold << "." << std::endl;
int thisDistance;
for (int i = 0; i < the_entries.size(); i++)
{
for (int j = i + 1; j < the_entries.size(); j++)
{
// we could use the_entries.size() instead of the_entries.at(i).size(), because this is a square matrix.
thisDistance = the_entries.at(i).at(j);
if (thisDistance < threshold)
{
std::vector<int> CurrentEdge(2);
CurrentEdge[0] = i;
CurrentEdge[1] = j;
TheEdges.push_back(CurrentEdge);
};
};
};
return TheEdges;
}
///////////////////////////////////////////
// Main Program: Extract edges from a distanceMatrix file.
///////////////////////////////////////////
int main(int argc, char** threshold_and_distanceMatrixfilename)
{
if (argc < 2 || argc > 3)
{
std::cerr << "Usage: ./distanceMatrixToSageGraph.o <threshold> <distanceMatrix_file_calculated_fromDGEsingleCell_data>" << std::endl;
return -1;
}
string distanceMatrixfilename = threshold_and_distanceMatrixfilename[2];
int threshold = std::stoi(threshold_and_distanceMatrixfilename[1]);
std::ifstream distanceMatrixFile(distanceMatrixfilename);
if (!distanceMatrixFile) {
std::cerr << "Error opening distanceMatrix file: " << distanceMatrixfilename << std::endl;
return -1;
}
string row; //LINE 88
std::getline(distanceMatrixFile, row); // discard the first row, which specifies the format of the file.
vector<vector<int>> the_entries;
while (std::getline(distanceMatrixFile, row))
{
std::stringstream row_as_stringstream(row);
int i; i = 0;
vector<string> row_as_vector;
while (row_as_stringstream.good())
{
string substr;
getline(row_as_stringstream, substr, ',');
row_as_vector.push_back( std::stoi(substr) );
};
the_entries.push_back(row_as_vector); //LINE 104
};
////////////////////////////////////////////////////////////
// Now we assemble the entries to an edges matrix, and write it into a Sage file:
////////////////////////////////////////////////////////////
std::vector<std::vector<int>> TheEdges = ConvertEntriesMatrixToEdges(the_entries, threshold);
char outputFilename[60]; strcpy(outputFilename, distanceMatrixfilename.c_str()); strcat(outputFilename, "AtThreshold"); string thrshld = std::to_string(threshold); strcat(outputFilename, thrshld.c_str()); strcat(outputFilename, ".txt");
writeGraphInSageFormat(outputFilename, TheEdges);
return 0;
}
第一个问题。你缺少的是程序名称是一个参数,所以
program arg1 arg2
是三个参数,argc
等于 3 而不是 2。你可以通过使用调试器自己找到这个(你真的需要学习如何使用一个,比在这里问要好得多)或者至少将 cout << "argc=" << argc << '\n';
添加到您的代码中。
第二个问题,您的原始代码是为逗号分隔值编写的,请参阅此处的逗号 getline(row_as_stringstream, substr, ',');
显然您需要将其更改为分号或 space 分隔值。
最重要的是,您需要学习使用调试器。尝试通过查看代码来调试程序并不容易。
解决方法:使用if (argc !=3)
和getline(row_as_stringstream, substr, ';')
这是我之前问题的延续:
我是 C++ 的新手,我正在尝试从我的主管那里调试这段代码。
原始代码以csv
文件作为输入,包含integers
的行和列
和 strings
。现在我们正在读取一个 txt
文件,其形状为:
TEXT
0; INT; INT; INT; INT; ...
0; INT; INT; INT; INT; ...
18 more lines of the above numbers and semicolons
在那个文件中,我在一个实例中用换行符替换了分号,在另一个实例中用空格替换了分号,因为我不确定我们需要哪个。
解决方法:使用带分号的txt
文件,但去掉行尾的分号.
if (argc < 2 || argc > 2)
似乎有问题。它抛出“用法:./a.o <> <>”错误消息。但是,两者都是严格不等式。这个if
不应该有 2 个参数吗?在原始代码中,它显示为if (argc < 2 || argc > 3)
,我将其改回。
编辑: 由于 john 也指出了 "program name is an argument",所以我实际上想要 3 而不是 2.两个
txt
文件(换行符和空格)似乎在下面产生相同的错误消息
错误信息:(对于int
阈值我尝试了各种值)
Registering only edges shorter than int.
terminate called after throwing an instance of 'std::out_of_range'
what(): vector::_M_range_check: __n (which is 1) >= this->size() (which is 1)
Aborted (core dumped)
想法:
当我们有一个简单的案例时,我知道此错误消息的含义,对于 example:
#include <vector>
int main()
{
std::vector<int> v;
v.push_back(123); // v has 1 element [0 to 0]
int x4 = v.at(3); // exception
}
我们得到一个异常,因为 v 有 1 个元素,而元素 3 不存在。
但是,在我的代码中,我不确定要查找的内容。
原始代码读取了带有行和列的 csv
,但在这种情况下,中间有空格的矩阵形式可能会导致问题。这是否意味着我只想要一个看起来像列向量的 txt
文件?那是我试过的一个文件,所以代码可能对列数不满意?
相关函数:
int main(int argc, char** threshold_and_distanceMatrixfilename)
{
if (argc < 2 || argc > 3)
{
std::cerr << "Usage: ./distanceMatrixToSageGraph.o <threshold>
<distanceMatrix_file_calculated_fromDGEsingleCell_data>" << std::endl;
return -1;
}
string distanceMatrixfilename = threshold_and_distanceMatrixfilename[2];
int threshold = std::stoi(threshold_and_distanceMatrixfilename[1]);
std::ifstream distanceMatrixFile(distanceMatrixfilename);
if (!distanceMatrixFile)
{
std::cerr << "Error opening distanceMatrix file: " << distanceMatrixfilename << std::endl;
return -1;
}
string row;
std::getline(distanceMatrixFile, row); // discard the first row, which specifies the format of the file.
vector<vector<int>> the_entries;
while (std::getline(distanceMatrixFile, row))
{
std::stringstream row_as_stringstream(row);
int i; i = 0;
vector<string> row_as_vector;
while (row_as_stringstream.good())
{
string substr;
getline(row_as_stringstream, substr, ',');
row_as_vector.push_back( std::stoi(substr) );
};
the_entries.push_back(row_as_vector); //LINE 104
};
}
整个代码:
// Convert distanceMatrix tables of protein interactions to SAGE graph.
///////////////////////////////////////////////////////////////////////////
#include <iostream>
#include <fstream>
#include <sstream>
#include <math.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <list>
#include <vector>
#include <tuple>
#include <algorithm>
using namespace std;
void writeGraphInSageFormat(string name, std::vector<std::vector<int>> TheEdges)
{
//////////////////////////////////////////////////////////////////////////////////////
// Write out the edges in SAGE format.
///////////////////////////////////////////////////////////////////////////////////////
int edgeNumber = TheEdges.size();
ofstream d1sageFile(name, ios::out);
d1sageFile << "g = Graph([" << endl;
for (int n = 0; n < edgeNumber; n++) {
d1sageFile << "(" << TheEdges[n][0] + 1 << "," << TheEdges[n][1] + 1 << ")," << endl;
}
d1sageFile << "])" << endl;
d1sageFile << "g.show()" << endl;
d1sageFile.close();
std::cout << "SAGE graph written into the file " << name << std::endl;
}
std::vector<std::vector<int>> ConvertEntriesMatrixToEdges(vector<vector<int>> the_entries, int threshold)
{
////////////////////////////////////////////////////////////////////////////////////////////
// Construct the edge-vertex incidence matrix (d_1) from the distanceMatrix entries matrix:
////////////////////////////////////////////////////////////////////////////////////////////
std::vector<std::string> proteinNames;
std::vector<std::vector<int>> TheEdges;
std::cout << "Registering only edges shorter than " << threshold << "." << std::endl;
int thisDistance;
for (int i = 0; i < the_entries.size(); i++)
{
for (int j = i + 1; j < the_entries.size(); j++)
{
// we could use the_entries.size() instead of the_entries.at(i).size(), because this is a square matrix.
thisDistance = the_entries.at(i).at(j);
if (thisDistance < threshold)
{
std::vector<int> CurrentEdge(2);
CurrentEdge[0] = i;
CurrentEdge[1] = j;
TheEdges.push_back(CurrentEdge);
};
};
};
return TheEdges;
}
///////////////////////////////////////////
// Main Program: Extract edges from a distanceMatrix file.
///////////////////////////////////////////
int main(int argc, char** threshold_and_distanceMatrixfilename)
{
if (argc < 2 || argc > 3)
{
std::cerr << "Usage: ./distanceMatrixToSageGraph.o <threshold> <distanceMatrix_file_calculated_fromDGEsingleCell_data>" << std::endl;
return -1;
}
string distanceMatrixfilename = threshold_and_distanceMatrixfilename[2];
int threshold = std::stoi(threshold_and_distanceMatrixfilename[1]);
std::ifstream distanceMatrixFile(distanceMatrixfilename);
if (!distanceMatrixFile) {
std::cerr << "Error opening distanceMatrix file: " << distanceMatrixfilename << std::endl;
return -1;
}
string row; //LINE 88
std::getline(distanceMatrixFile, row); // discard the first row, which specifies the format of the file.
vector<vector<int>> the_entries;
while (std::getline(distanceMatrixFile, row))
{
std::stringstream row_as_stringstream(row);
int i; i = 0;
vector<string> row_as_vector;
while (row_as_stringstream.good())
{
string substr;
getline(row_as_stringstream, substr, ',');
row_as_vector.push_back( std::stoi(substr) );
};
the_entries.push_back(row_as_vector); //LINE 104
};
////////////////////////////////////////////////////////////
// Now we assemble the entries to an edges matrix, and write it into a Sage file:
////////////////////////////////////////////////////////////
std::vector<std::vector<int>> TheEdges = ConvertEntriesMatrixToEdges(the_entries, threshold);
char outputFilename[60]; strcpy(outputFilename, distanceMatrixfilename.c_str()); strcat(outputFilename, "AtThreshold"); string thrshld = std::to_string(threshold); strcat(outputFilename, thrshld.c_str()); strcat(outputFilename, ".txt");
writeGraphInSageFormat(outputFilename, TheEdges);
return 0;
}
第一个问题。你缺少的是程序名称是一个参数,所以
program arg1 arg2
是三个参数,argc
等于 3 而不是 2。你可以通过使用调试器自己找到这个(你真的需要学习如何使用一个,比在这里问要好得多)或者至少将 cout << "argc=" << argc << '\n';
添加到您的代码中。
第二个问题,您的原始代码是为逗号分隔值编写的,请参阅此处的逗号 getline(row_as_stringstream, substr, ',');
显然您需要将其更改为分号或 space 分隔值。
最重要的是,您需要学习使用调试器。尝试通过查看代码来调试程序并不容易。