通过引用传递时的误解(C 结构)
Misunderstanding something when passing by reference (C structures)
我正在编写一些基本的 C 代码,运行 解决了一个我无法解决的问题。所以我目前的设置是我已经创建了一个简单的结构:
struct UserInfo
{
WCHAR* UserName;
WCHAR* ComputerName;
}
我想从我的 main 创建该结构的一个实例,通过引用将结构传递给两个函数,每个函数将填充两个字段之一。我的主要代码是:
void main()
{
struct UserInfo userInfo;
GetUserName(&userInfo);
GetComputerName(&userInfo);
return 0;
}
两个函数如下:
BOOL GetUserName(struct UserInfo* userInfo)
/*
Function calls the winapi function GetUserNameW to return the current
username in widechar format.
*/
{
WCHAR UserName[USERNAME_MAXSIZE + 1];
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
if (!GetUserNameW(UserName, &UserNameSize))
{
if (&UserNameSize != USERNAME_MAXSIZE + 1)
{
if (!GetUserNameW(UserName, &UserNameSize)) return FALSE;
}
else return FALSE;
}
userInfo->UserName = UserName;
return TRUE;
}
和
BOOL GetComputerName(struct UserInfo* userInfo)
{
LPWSTR ComputerBuffer[MAX_PATH];
DWORD ComputerBufferSize = MAX_PATH;
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize))
{
if (&ComputerBufferSize != MAX_PATH)
{
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize)) return FALSE;
}
else return FALSE;
}
userInfo->ComputerName = ComputerBuffer;
return TRUE;
}
我遇到的问题是,当调用第二个函数时,存储在第一个值中的数据似乎被覆盖了。因此,例如,在执行代码时,第一个函数使用指向我的系统用户名的指针正确填充 userInfo->UserName。
当调用第二个函数时,用户 userInfo->UserName 值似乎被覆盖,第二个函数运行正常并且 userInfo->ComputerName 被正确填充。我很困惑为什么会这样?如果我像这样将这些功能合并为一个:
BOOL GetData(struct UserInfo* userInfo)
{
WCHAR UserName[USERNAME_MAXSIZE + 1];
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
LPWSTR ComputerBuffer[MAX_PATH];
DWORD ComputerBufferSize = MAX_PATH;
if (!GetUserNameW(UserName, &UserNameSize))
{
if (&UserNameSize != USERNAME_MAXSIZE + 1)
{
if (!GetUserNameW(UserName, &UserNameSize)) return FALSE;
}
else return FALSE;
}
userInfo->UserName = UserName;
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize))
{
if (&ComputerBufferSize != MAX_PATH)
{
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize)) return FALSE;
}
else return FALSE;
}
userInfo->ComputerName = ComputerBuffer;
return TRUE;
}
这一切都按预期工作,我是否误解了有关通过引用传递的内容?根据我的理解, &userInfo 基本上是传递一个指向我的结构的指针,而 userInfo->somefield 实际上是在修改我的结构,而不是像按值传递那样的复制结构。我不明白为什么当将相同的结构传递给不同的函数时,每个函数修改不同的字段,它们会相互干扰?
在此先感谢您对理解这一点的任何帮助。
数组UserName
和ComputerBuffer
是函数中的非静态局部数组。这意味着它们的生命在从函数返回时结束,因此您不能在从函数返回后使用指向它们的指针。
你应该在堆上分配一些缓冲区,这样数据就不会在返回时被擦除。
您还应该使用 WCHAR
而不是 LPWSTR
作为 ComputerBuffer
的元素,因为要分配的成员 ComputerName
的类型为 WCHAR*
。
而不是这些:
WCHAR UserName[USERNAME_MAXSIZE + 1];
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
LPWSTR ComputerBuffer[MAX_PATH];
DWORD ComputerBufferSize = MAX_PATH;
你应该这样做:
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
WCHAR *UserName = malloc(sizeof(*UserName) * UserNameSize);
DWORD ComputerBufferSize = MAX_PATH;
WCHAR *ComputerBuffer = malloc(sizeof(*ComputerBuffer ) * ComputerBufferSize);
你应该添加
#include <stdlib.h>
使用 malloc()
(如果尚不存在)。
我正在编写一些基本的 C 代码,运行 解决了一个我无法解决的问题。所以我目前的设置是我已经创建了一个简单的结构:
struct UserInfo
{
WCHAR* UserName;
WCHAR* ComputerName;
}
我想从我的 main 创建该结构的一个实例,通过引用将结构传递给两个函数,每个函数将填充两个字段之一。我的主要代码是:
void main()
{
struct UserInfo userInfo;
GetUserName(&userInfo);
GetComputerName(&userInfo);
return 0;
}
两个函数如下:
BOOL GetUserName(struct UserInfo* userInfo)
/*
Function calls the winapi function GetUserNameW to return the current
username in widechar format.
*/
{
WCHAR UserName[USERNAME_MAXSIZE + 1];
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
if (!GetUserNameW(UserName, &UserNameSize))
{
if (&UserNameSize != USERNAME_MAXSIZE + 1)
{
if (!GetUserNameW(UserName, &UserNameSize)) return FALSE;
}
else return FALSE;
}
userInfo->UserName = UserName;
return TRUE;
}
和
BOOL GetComputerName(struct UserInfo* userInfo)
{
LPWSTR ComputerBuffer[MAX_PATH];
DWORD ComputerBufferSize = MAX_PATH;
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize))
{
if (&ComputerBufferSize != MAX_PATH)
{
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize)) return FALSE;
}
else return FALSE;
}
userInfo->ComputerName = ComputerBuffer;
return TRUE;
}
我遇到的问题是,当调用第二个函数时,存储在第一个值中的数据似乎被覆盖了。因此,例如,在执行代码时,第一个函数使用指向我的系统用户名的指针正确填充 userInfo->UserName。
当调用第二个函数时,用户 userInfo->UserName 值似乎被覆盖,第二个函数运行正常并且 userInfo->ComputerName 被正确填充。我很困惑为什么会这样?如果我像这样将这些功能合并为一个:
BOOL GetData(struct UserInfo* userInfo)
{
WCHAR UserName[USERNAME_MAXSIZE + 1];
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
LPWSTR ComputerBuffer[MAX_PATH];
DWORD ComputerBufferSize = MAX_PATH;
if (!GetUserNameW(UserName, &UserNameSize))
{
if (&UserNameSize != USERNAME_MAXSIZE + 1)
{
if (!GetUserNameW(UserName, &UserNameSize)) return FALSE;
}
else return FALSE;
}
userInfo->UserName = UserName;
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize))
{
if (&ComputerBufferSize != MAX_PATH)
{
if (!GetComputerNameW(ComputerBuffer, &ComputerBufferSize)) return FALSE;
}
else return FALSE;
}
userInfo->ComputerName = ComputerBuffer;
return TRUE;
}
这一切都按预期工作,我是否误解了有关通过引用传递的内容?根据我的理解, &userInfo 基本上是传递一个指向我的结构的指针,而 userInfo->somefield 实际上是在修改我的结构,而不是像按值传递那样的复制结构。我不明白为什么当将相同的结构传递给不同的函数时,每个函数修改不同的字段,它们会相互干扰?
在此先感谢您对理解这一点的任何帮助。
数组UserName
和ComputerBuffer
是函数中的非静态局部数组。这意味着它们的生命在从函数返回时结束,因此您不能在从函数返回后使用指向它们的指针。
你应该在堆上分配一些缓冲区,这样数据就不会在返回时被擦除。
您还应该使用 WCHAR
而不是 LPWSTR
作为 ComputerBuffer
的元素,因为要分配的成员 ComputerName
的类型为 WCHAR*
。
而不是这些:
WCHAR UserName[USERNAME_MAXSIZE + 1];
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
LPWSTR ComputerBuffer[MAX_PATH];
DWORD ComputerBufferSize = MAX_PATH;
你应该这样做:
DWORD UserNameSize = USERNAME_MAXSIZE + 1;
WCHAR *UserName = malloc(sizeof(*UserName) * UserNameSize);
DWORD ComputerBufferSize = MAX_PATH;
WCHAR *ComputerBuffer = malloc(sizeof(*ComputerBuffer ) * ComputerBufferSize);
你应该添加
#include <stdlib.h>
使用 malloc()
(如果尚不存在)。