分辨
我试图制作一个简单的文件加载器。 我的目标是将着色器文件(纯文本文件)中的文本转换为char *,我将在稍后编译。
我尝试过这个功能:
char* load_shader(char* pURL)
{
FILE *shaderFile;
char* pShader;
// File opening
fopen_s( &shaderFile, pURL, "r" );
if ( shaderFile == NULL )
return "FILE_ER";
// File size
fseek (shaderFile , 0 , SEEK_END);
int lSize = ftell (shaderFile);
rewind (shaderFile);
// Allocating size to store the content
pShader = (char*) malloc (sizeof(char) * lSize);
if (pShader == NULL)
{
fputs ("Memory error", stderr);
return "MEM_ER";
}
// copy the file into the buffer:
int result = fread (pShader, sizeof(char), lSize, shaderFile);
if (result != lSize)
{
// size of file 106/113
cout << "size of file " << result << "/" << lSize << endl;
fputs ("Reading error", stderr);
return "READ_ER";
}
// Terminate
fclose (shaderFile);
return 0;
}
但正如你在代码中看到的那样,我在进程结束时有一个奇怪的大小差异,这使我的函数崩溃。
我必须说我是C中的初学者,所以我可能错过了关于内存分配,类型,指针的一些细微差别...... 如何解决此尺寸问题?
* 编辑1:
首先,我不应该在结束时返回0但是pShader;这似乎是程序崩溃的原因。 然后,我将reult的类型更改为size_t,并将一个结束字符添加到pShader,添加pShdaer [result] =&#39; / 0&#39 ;;在声明后,我可以正确显示它。 最后,正如@JamesKanze建议的那样,我把fopen_s变成了fopen,因为之前在我的情况下没有用。
答案 0 :(得分:0)
首先,对于这种原始访问,您可能会更好
使用系统级功能:CreateFile
或open
,
ReadFile
或read
以及CloseHandle
或close
GetFileSize
或stat
来获取尺寸。使用FILE*
或
std::filebuf
只会引入额外的级别
缓冲和处理,在您的情况下无益。
至于您所看到的内容:无法保证ftell
将返回任何可利用的数字值;它可能
很好只是一个神奇的饼干。在大多数现有系统中,它
是字节偏移到物理文件中,但在任何非Unix上
系统,物理文件的偏移量不会直接映射
到您正在阅读的逻辑文件,除非您打开该文件
二进制模式。如果您使用"rb"
打开该文件,那么您就可以了
可能看到相同的值。 (从理论上讲,你可以得到
文件末尾的额外0,但实际上是操作系统
发生的事情要么已经灭绝,要么仅用于遗产
大型机。)
编辑:
由于答案说明已被删除:你应该循环
在fread
上,直到它返回0(之前将errno
设置为0
每次调用,并在返回后检查它是否有
由于错误或因为它到达而返回的函数
文件结束)。话虽如此:如果你是平常的话
Windows或Unix系统,该文件是机器本地的,
并且不会太大,fread
将一次性读取所有内容。该
你看到的大小差异(给定数值
你发布的)几乎肯定是由于这两个事实
字节Windows行结尾被映射到单个'\n'
字符。为避免这种情况,您必须以二进制模式打开;
或者,如果你真的在处理文本(并希望
这个映射),你可以忽略你的额外字节
缓冲区,在最后一个字节后设置'\0'
终止符
实际上读了。