我的数据是放在了一组文本中,现在我要从这些文本文件中读取数据,然后生成一维数组。文本的格式如下:
001.txt:
11
13
0
5
6
400
......
数据量很大,大概是2000,000左右。
=======================================================================================
我想到了两个方法,第一个,用BYTE* ptr,指针指向首地址,但是我对指针是在是不明白,我的语句如下
int temp;
fp=fopen("*.txt","r");//(这里的*.txt)只不过是指这一系列的文本文件名称,没有具体写出代码
while (!feof(fp)){
fscanf(fp,"%d\n",&temp);
(*ptr)=temp;
ptr++;
}
fclose(fp);
运行时提示错误,请指正!第二个,用CArray<int,int> temp_array;
int temp;
fp=fopen("*.txt","r");
while (!feof(fp)){
fscanf(fp,"%d\n",&temp);
temp_array.add(temp);
}
运行时根本跑不动,近似于死机状态。
===================================================================================
各位有没有什么好的方法?!!!
001.txt:
11
13
0
5
6
400
......
数据量很大,大概是2000,000左右。
=======================================================================================
我想到了两个方法,第一个,用BYTE* ptr,指针指向首地址,但是我对指针是在是不明白,我的语句如下
int temp;
fp=fopen("*.txt","r");//(这里的*.txt)只不过是指这一系列的文本文件名称,没有具体写出代码
while (!feof(fp)){
fscanf(fp,"%d\n",&temp);
(*ptr)=temp;
ptr++;
}
fclose(fp);
运行时提示错误,请指正!第二个,用CArray<int,int> temp_array;
int temp;
fp=fopen("*.txt","r");
while (!feof(fp)){
fscanf(fp,"%d\n",&temp);
temp_array.add(temp);
}
运行时根本跑不动,近似于死机状态。
===================================================================================
各位有没有什么好的方法?!!!
还有,你说文件中的数据是生成BYTE的数组,怎么我有看到400(>255)可不是byte取值范围。
是不是int *ptr;然后就可以
(*ptr)=temp;ptr++了?另外,如果申请内存,就一定会更快么?多谢!
CStringArray FileContainer;
bFileExist=fMyFile.Open(m_sFileName, CFile::modeRead); if(!bFileExist)
{
return FALSE;
} CString strline;
FileContainer.RemoveAll(); while(fMyFile.ReadString(strline))
{
FileContainer.Add(strline);
} fMyFile.Close();
至于分配空间,你访问一个指针之前必须为它指向的位置分配空间的啊,而不是分配了空间会更快。
分派空间可以用malloc函数。如果你声明的是一个数组,然后又把指针指向数组首地址,那就已经分配了do空间了。
newbiestar说的覆盖,应该没有这样的问题。
至于采用什么格式,如果是经常存取的话,二进制要好得多,速度快,而且可以随机访问;但是如果在很长一段时间只读写一次的话,文本也无所谓啦。
另外,dos格式的文本是"\r\n"换行的,我不知道你用"\n"读取会不会有问题。
总时间就是2000000*1ms = 2000秒 /60 = 30分钟左右用CFile:
char *p = NULL;
try{
CFile cf("*.txt", CFile::modeRead);
DWORD dwlen = cf.GetLength();
p = new char[dwlen];
if(p) cf.HugeRead(p,dwlen);
}
catch(CFileExecption &e)
{
...
}
之后再用程序来判断\r\n
对于你采用的第二种方式,建议用
CByteArray
且做如下调用:
const int KMAXSIZE = 3000000; //一个通常情况下大于实际可能数组大小的值
CByteArray temp_array;
temp_array.SetSize( KMAXSIZE, KMAXSIZE / 8 );
这样CByteArray的运算性能表现上会接近于指针运算处理数组
调用完以后可以看需要调用方法FreeExtra释放多出来的空间
C*类的效率肯定比数组差多了,你还是用数组就好。
至于分配空间,你访问一个指针之前必须为它指向的位置分配空间的啊,而不是分配了空间会更快。
分派空间可以用malloc函数。如果你声明的是一个数组,然后又把指针指向数组首地址,那就已经分配了do空间了。
newbiestar说的覆盖,应该没有这样的问题。
至于采用什么格式,如果是经常存取的话,二进制要好得多,速度快,而且可以随机访问;但是如果在很长一段时间只读写一次的话,文本也无所谓啦。
另外,dos格式的文本是"\r\n"换行的,我不知道你用"\n"读取会不会有问题。
==========================================
你不相信么?那你就去试试看,BYTE*就是unsigned char,你看看你调用了++操作符以后地址+4字节还是+1字节……另外\n和\r\n没有区别,因为fopen的参数是"r"而不是"rb",所以不存在差别,都是一样的,fscanf自己能认得这些东西……
方式一:
int temp;
fp=fopen("*.txt","r");//(这里的*.txt)只不过是指这一系列的文本文件名称,没有具体写出代码
while (!feof(fp)){
fscanf(fp,"%d\n",&temp);
(*ptr)=temp; //看这,你怎么可以把一个整型数赋给字节类型变量呢?
//改成(*ptr) = (BYTE)temp; 就对了
ptr++;
}
fclose(fp);
CString strFileName;
long int nlen;
//open and read file obtain information
CFileDialog Dlg(true,"txt",NULL,OFN_HIDEREADONLY| OFN_OVERWRITEPROMPT, "*.TXT | *.txt",this);
if (Dlg.DoModal() == IDOK)
{
strFileName = Dlg.GetPathName();
m_Path = strFileName;
UpdateData(false);
if(pfile.Open(strFileName.GetBuffer(0),CFile::modeRead))
{
BYTE* buffer;
//obtain file length
nlen = pfile.GetLength();
if (nlen)
{
buffer = new BYTE[nDataLen];
if(pfile.ReadHuge(buffer,nDataLen)) //read huge file obtain file length
{
HandleData(buffer,nDataLen);
}
if(buffer != NULL)
{
delete[] buffer;
pfile.Close();
}
}
}
}
void CRemovenoiseView::HandleData(BYTE *buffer, int nLen)
{
//这里就可以对数组进行操作了
}