我对C ++编程比较陌生,而且我做的代码没有达到预期的效果。
代码有点长[粘贴在最后以供参考]但我只想指出我对代码的关注:
我在while循环中定义了一个类的对象:
...
objVec[obj_i] = new ChipSeqRegion(refID, strand, midPoint, start, end, posArray, frac_posArray, negArray, frac_negArray);
//testing
cout<<"printing object number: "<<obj_i<<endl;
objVec[obj_i]->PrintID();
cout<<"printing frac pos array: "<<endl;
objVec[obj_i]->PrintFracPosArray();
obj_i++;
}
objVec[0]->PrintID();
cout<<endl;
objVec[0]->PrintFracPosArray();
cout<<endl;
objVec[1]->PrintID();
objVec[1]->PrintFracPosArray();
cout<<endl;
objVec[2]->PrintID();
objVec[2]->PrintFracPosArray();
}
在上面的代码片段中,PrintID和PrintFracPosArray只是程序[同一类的成员]来打印变量/数组的内容。
现在,如果我尝试在循环中打印对象属性refID和posArray,那么所有打印的值都会出现不同的分配和预期。
但是在循环之外,printID属性以[按预期]唯一打印值,但posArray属性只重复循环中最后分配的值。 我想在循环之外唯一访问所有值,这是我关心的问题。
我确信这可能来自范围冲突或变量传递的方式。
任何帮助都会很棒!!!
提前致谢。 快速查看下面的详细代码可以澄清任何问题:
详细代码:[对不良表现道歉]
#include <iostream>
#include <string>
#include <fstream>
#include <cstring>
#include <sstream>
#include <cstdlib>
#include <vector>
#include <iomanip>
#include <cmath>
#include "api/BamReader.h"
#include "api/BamWriter.h"
#include "api/BamAlignment.h"
#include "api/BamAux.h"
using namespace std;
using namespace BamTools;
BamReader reader;
BamAlignment al;
int const windowSize = 10;
int halfWindowSize = windowSize/2;
int const N = windowSize + 1;
//determine the gap score
float gap = -2;
//default value for matrix F
double negNum = -100000;
float F[N][N];
int xTraceBack[N][N];
int yTraceBack[N][N];
float maxScore;
int x_coord = 0;
int y_coord = 0;
//collections of arrays from chipSeq data after loading data
class ChipSeqRegion{
private:
int ref_id, mid_p, start_p, end_p;
char genomeStrand;
float* pos_array;
float* frac_positiveArray;
float* neg_array;
float* frac_negativeArray;
float* gap;
public:
ChipSeqRegion (int refID, char strand, int midPoint, int start, int end, float* posArray, float* frac_posArray, float* negArray, float* frac_negArray);
//accessors
int GetRefID(){return ref_id;}
int GetMidPoint(){return mid_p;}
void PrintID();
void PrintFracPosArray();
//destructor
~ChipSeqRegion(){
delete [] pos_array;
delete [] frac_positiveArray;
delete [] neg_array;
delete [] frac_negativeArray;
}
};
ChipSeqRegion::ChipSeqRegion(int refID, char strand, int midPoint, int start, int end, float* posArray, float* frac_posArray, float* negArray, float* frac_negArray){
ref_id = refID;
genomeStrand = strand;
mid_p = midPoint;
start_p = start;
end_p = end;
pos_array = posArray;
frac_positiveArray = frac_posArray;
neg_array = negArray;
frac_negativeArray = frac_negArray;
}
void ChipSeqRegion::PrintID(){
cout<<"ref id is: "<<ref_id<<endl;
}
void ChipSeqRegion::PrintFracPosArray(){
cout<<"this is raw pos data"<<endl;
for (int i = 0; i<windowSize; i++){
cout<<pos_array[i]<<'\t';
}
cout<<"this is frac data"<<endl;
for (int i = 0; i<windowSize; i++){
cout<<frac_positiveArray[i]<<'\t';
}
cout<<endl;
}
class ChipSeqLoader{
public:
void LoadData (string bamFileName, string coordFileName);
void GetRegions();
private:
string nameOfBamFile;
string nameOfCoordFile;
};
void ChipSeqLoader::LoadData(string bamFileName, string coordFileName){
nameOfBamFile = bamFileName;
nameOfCoordFile = coordFileName;
int obj_i = 0;
int objSize = 6;
ChipSeqRegion **objVec = new ChipSeqRegion* [objSize];
//reading coordinates
ifstream CoordFile;
char chrom[5], strand;
string sChr1, sChr2, withmotif, dot;
int start, end, midPoint;
float tag;
CoordFile.open(coordFileName.c_str());
if (CoordFile.is_open()){
while (!CoordFile.eof()){
CoordFile>>chrom;
CoordFile>>withmotif;
CoordFile>>dot;
CoordFile>>start;
CoordFile>>end;
CoordFile>>tag;
CoordFile>>strand;
CoordFile.ignore(200,'\n');
midPoint = (start+end)/2;
ostringstream convert1;
ostringstream convert2;
convert1<<chrom[3];
convert2<<chrom[4];
sChr1 = convert1.str();
sChr2 = convert2.str();
string sChrom;
sChrom = sChr1+sChr2;
int refID;
if (sChr1 =="X\0"){
refID = 19;
}else if (sChr1 == "Y\0"){
refID = 20;
}else{
refID = atoi(sChrom.c_str())-1;
}
int intStrand;
if (strand == '+'){
intStrand = 0;
}else if (strand == '-'){
intStrand = 1;
}
cout<<endl;
cout<<sChrom<<'\t'<<refID<<'\t'<<start<<'\t'<<end<<'\t'<<midPoint<<'\t'
<<strand<<'\t'<<intStrand<<endl;
//get information from the coordinates to return array
BamRegion region(refID, midPoint-600, refID, midPoint+600);
reader.SetRegion(region);
if(!reader.SetRegion(region)){
std::cout<<"could not set region."<<endl;
}
float posArray[windowSize];
float negArray[windowSize];
float frac_posArray[windowSize];
float frac_negArray[windowSize];
for (int index = 0; index < windowSize; index ++){
posArray[index] = 0;
negArray[index] = 0;
}
int posPosition;
int negPosition;
//if reverse strand, calculate and return the end position
//if positive strand, return the position
//put them in separate arrays
while (reader.GetNextAlignment(al)){
if (al.MapQuality>0 && al.IsReverseStrand()== true){
negPosition = al.GetEndPosition();
if (negPosition>=midPoint-halfWindowSize && negPosition <midPoint+halfWindowSize){
negArray[negPosition-midPoint+halfWindowSize]++;
}
}else if (al.MapQuality>0){
posPosition = al.Position;
if (posPosition>=midPoint-halfWindowSize && posPosition <midPoint+halfWindowSize){
posArray[posPosition-midPoint+halfWindowSize]++;
}
}
}
float posMax = 0, negMax = 0, max = 0;
float temp;
for (int i= 0; i<windowSize; i++){
temp = posArray[i];
if (temp>posMax){
posMax = temp;
}
}
for (int i = 0; i<windowSize; i++){
temp = negArray[i];
if (temp>negMax){
negMax = temp;
}
}
if (posMax>=negMax){
max = posMax;
}else{
max = negMax;
}
for (int i = 0; i<windowSize; i++){
frac_posArray[i] = posArray[i]/max;
frac_negArray[i] = negArray[i]/max;
}
objVec[obj_i] = new ChipSeqRegion(refID, strand, midPoint, start, end, posArray, frac_posArray, negArray, frac_negArray);
//testing
cout<<"printing object number: "<<obj_i<<endl;
objVec[obj_i]->PrintID();
cout<<"printing frac pos array: "<<endl;
objVec[obj_i]->PrintFracPosArray();
obj_i++;
}
objVec[0]->PrintID();
cout<<endl;
objVec[0]->PrintFracPosArray();
cout<<endl;
objVec[1]->PrintID();
objVec[1]->PrintFracPosArray();
cout<<endl;
objVec[2]->PrintID();
objVec[2]->PrintFracPosArray();
}
}
int main(int argc, char* argv[]) {
string bamFileName, coordFileName;
if (argc == 3){
bamFileName = argv[1];
coordFileName = argv[2];
}else{
std::cout << "Wrong number of arguments." <<endl;
return 1;
}
if (!reader.Open(bamFileName)){
std::cout<< "Could not open input Bam file." <<endl;
return 1;
}
if (!reader.LocateIndex()){
std::cout<<"Could not locate index file."<<endl;
return 1;
}
ChipSeqLoader loader;
loader.LoadData(bamFileName, coordFileName);
return 0;
}
答案 0 :(得分:0)
所有对象都指向同一条数据,即循环中定义的posArray
和frac_posArray
:如果查看ChipSeqRegion
类构造函数,它会接受2个数组(与上面引用的数组名称相同),即。指向内存中数据序列的2个指针。构造函数中的这些指针只是在实例字段中复制:
pos_array = posArray;
frac_positiveArray = frac_posArray;
而不是复制数组内容,因为它应该是:
pos_array = new int[windowSize];
memcpy(pos_array,posArray, sizeof(int)*windowSize); // or use std::copy_n
frac_positiveArray = new int[windowSize];
memcpy(frac_positivearray,frac_posArray, sizeof(int)*windowSize); // or use std::copy_n
您可能会遇到与该类中其他数组相同的问题。