假设我的程序包含一个由Customer
s组成的未知长度的数组。
这里是客户结构:
struct Customer
{
char* lastname;
char* firstname;
int money;
};
在这里 - 一个数组:
Customer* CustomerDB;
好。但问题是我想在运行时动态添加和删除客户。我不希望在声明期间或运行期间分配100个客户 - 我希望在需要时一次分配一个。
考虑一个简单的AddCustomer函数,它分配内存,输入给定的数据然后递增一个计数器(这可能是迭代所需的)。
这是我的主要问题。
我想要的是数组的行为与使用100个数组而不是动态数组声明的数组完全相同。
上面的客户计划只是一个示例,请不要告诉我这样做那个或那个坏主意。
如何为上述代码创建AddCustomer
函数?
我有必要遍历CustomerDB
答案 0 :(得分:6)
使用标准模板库std :: vector或指针向量。
答案 1 :(得分:3)
使用标准库容器,例如vector,deque或list。
答案 2 :(得分:2)
我认为AddCustomer函数可能是这样实现的:
void AddCustomer(Customer** db, int current_count);
可以根据realloc完成内存重新分配。
然而,你确实意识到你没有利用C ++提供的任何东西,所以你可能只是把它作为一个C问题发布(在C ++中,这是一个很简单的vector / deque / list和push_back)?
答案 3 :(得分:0)
如果你可以使用std::vector
或类似的,使用它,它们是专门针对这类问题而构建的。我还会同时将原始char *
替换为std::string
。
如果您坚持上述方法,则可能需要在大小更改时使用realloc()
更改已分配数组的大小。然而,这是一种非常手动的方式来实现矢量和放大器的组合。字符串可以更容易地为您做,并且没有潜在的资源泄漏。
答案 4 :(得分:0)
这里只是一些想法
根据您的要求判断,如果您使用列表而不是数组会更好。列表更适合您对动态的要求,并且没有最大限制。
您可以使用每个列表元素中的指针创建自己的链接列表,也可以使用std :: dequeue或类似命令,但无论如何您都需要处理结构中指针指向的内容。您的示例中最简单的情况可能是使用std :: string而不是指针 - 然后字符串会自动复制,您不必关心内存(或使用boost :: shared_array作为指针)。
struct Customer
{
string lastname;
string firstname;
int money;
};
只是我的2c
答案 5 :(得分:0)
正如你所说,这不是做事的“正确”方式 - 而是你所要求的。
typedef struct _tag_Customer {
char *LastName;
char *FirstName;
double Money;
} CUSTOMER, *LPCUSTOMER;
typedef struct _tag_Customers {
CUSTOMER *Collection;
int Count;
} CUSTOMERS, *LPCUSTOMERS;
LPCUSTOMER AddCustomer(LPCUSTOMERS pCustomers, const char *sLastName, const char *sFirstName, double dMoney)
{
int iRequiredMemory = (sizeof(CUSTOMER) * (pCustomers->Count + 1));
if(!(pCustomers->Collection = (LPCUSTOMER) realloc(pCustomers->Collection, iRequiredMemory)))
{
return NULL; //Memory allocation error.
}
LPCUSTOMER pCutsomer = &pCustomers->Collection[pCustomers->Count];
pCustomers->Count++;
iRequiredMemory = strlen(sLastName) + 1;
pCutsomer->LastName = (char *) calloc(iRequiredMemory, sizeof(char));
strcpy(pCutsomer->LastName, sLastName);
iRequiredMemory = strlen(sFirstName) + 1;
pCutsomer->FirstName = (char *) calloc(iRequiredMemory, sizeof(char));
strcpy(pCutsomer->FirstName, sLastName);
pCutsomer->Money = dMoney;
return pCutsomer;
}
void main(void)
{
CUSTOMERS Database;
memset(&Database, 0, sizeof(CUSTOMERS));
AddCustomer(&Database, "Smith", "Joe", 100.99);
AddCustomer(&Database, "Jackson", "Jane", 100.99);
AddCustomer(&Database, "Doe", "John", 100.99);
//You'll need to free the Memory, of course.
}