我找到了C片段来获取当前工作目录from here。基本上,代码是:
char directory[_MAX_PATH];
getcwd(directory, sizeof(directory))
我想将它抽象到另一个函数中,在另一个文件中(如果需要,可以在不同的平台上进行交换)。
目前,我有外部文件
void getCurrentDirectory(char *directory) {
getcwd(directory, sizeof(directory));
}
并在主文件中
char directory[100];
getCurrentDirectory(directory);
printf("%s", *directory);
然而,当打印到屏幕时,我得到废话(可能尝试将内存位置打印为字符串?)
我确信这对非初学者来说是非常明显的。发生了什么事?
编辑:我在Windows 7上,顺便说一下
感谢。
答案 0 :(得分:2)
您将char *的大小传递给getcwd,而不是数组的大小。
将尺寸参数传递给您的函数。
void getCurrentDirectory(char *directory, size_t size) {
getcwd(directory, size);
}
然后:
char directory[100];
getCurrentDirectory(directory, sizeof(directory));
printf("%s", *directory);
此外,如果您使用的是Windows,则应该将数组大小更改为预定义的MAX_PATH
,以避免潜在的缓冲区溢出。 getcwd需要一个长度,但我不认为所有的文件函数都可以。
答案 1 :(得分:2)
这一行:
printf("%s", *directory);
应该是:
printf("%s", directory);
您将第一个元素(目录[0])传递给printf,而不是指向char数组的指针。
答案 2 :(得分:2)
如果是C ++,我建议尽可能使用boost::filesystem,这会隐藏所有底层平台细节和为您提供C ++样式接口而不是缓冲区溢出C函数
答案 3 :(得分:2)
你在这里犯了很多错误:
void getCurrentDirectory(char *directory)
{
getcwd(directory, sizeof(directory));
}
错误1:
`sizeof(directory)`
给出指针的大小,准确地说是char *。您的目的是传递数组的大小,而不是指针大小。
错误2:
`printf("%s", *directory);`
将数组的第一个元素传递给printf而不是数组的地址。您的目的是打印整个数组而不仅仅是第一个元素。
更正解决方案
你应该这样做
void getCurrentDirectory(char *directory, size_t arrSize)
{ ^^^^^^^^^^^^^^
getcwd(directory, arrSize);
}
数组的大小是显式传递的,因此函数可以使用它。
在main中打印数组的内容时:
printf("%s", directory);
答案 4 :(得分:1)
您应该在本地分配缓冲区(必要时) 长度是已知的,实际长度需要知道)和 返回一个字符串:
std::string
getCurrentDirectory()
{
char results[_MAX_PATH];
if ( getcwd( results, sizeof(results) ) == NULL )
throw std::ios_base::failure( "Could not get current directory" );
return std::string( results );
}
另请注意,_MAX_PATH
只是猜测;实际最大值是
不是编译时常量(因为它取决于文件
系统)。考虑到这一点的实现可能会
看起来像:
std::string
getCurrentDirectory()
{
long length = pathconf( ".", _PC_PATH_MAX );
if ( length == -1 )
throw std::ios_base::failure(
"Could not determine necessary buffer length to get current directory" );
std::string results( length, '\0' );
if ( getcwd( &results[0], results.size() ) == NULL )
throw std::ios_base::failure( "Could not get current directory" );
results.resize( strlen( results.c_str() );
return results;
}
然而,如果程序只是进行,这可能是过度的 用于没有NFS或SMB安装驱动器的个人系统。
答案 5 :(得分:1)
因为它是C ++,为什么不这样做:
std::string getCurrentDirectory()
{
char directory[_MAX_PATH] = {};
getcwd(directory, sizeof(directory));
return directory;
}
答案 6 :(得分:0)
您无法使用sizeof
找到指针所指向的内存块的大小。它将评估指针本身的大小。
将您的功能更改为:
void getCurrentDirectory(char *directory, size_t buf_max)
{
getcwd(directory, buf_max);
}
答案 7 :(得分:0)
现在回答你的问题:
当getcwd由于某种原因失败时,directory
指向的数组内容(在您的情况下)是未定义的。因此,在您的错误实施中,您将在大多数情况下看到垃圾。 (另外,你应该检查getcwd
的返回值,它失败时返回-1)
现在,您的情况失败的原因是您使用sizeof(directory)
指定的大小只是指针的大小(可能是4)和当前工作目录名称中的字符正在尝试打印的不止于此。这适用于大小为3或更小的目录。
而且,最后这里的许多人已经向你解释了如何解决它。