C ++ malloc - 动态数组

时间:2010-02-23 15:43:53

标签: c++ arrays malloc

假设我的程序包含一个由Customer s组成的未知长度的数组。

这里是客户结构:

struct Customer
{
 char* lastname;
 char* firstname;
 int money;
};

在这里 - 一个数组:

Customer* CustomerDB;

好。但问题是我想在运行时动态添加和删除客户。我不希望在声明期间或运行期间分配100个客户 - 我希望在需要时一次分配一个。

考虑一个简单的AddCustomer函数,它分配内存,输入给定的数据然后递增一个计数器(这可能是迭代所需的)。

这是我的主要问题。

我想要的是数组的行为与使用100个数组而不是动态数组声明的数组完全相同。

上面的客户计划只是一个示例,请不要告诉我这样做那个或那个坏主意。

  • 如何为上述代码创建AddCustomer函数?

  • 我有必要遍历CustomerDB

6 个答案:

答案 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.
}