Почему виртуальная память не уменьшилась при выделении динамической c памяти - PullRequest
0 голосов
/ 06 апреля 2020

Почему при попытке выделить байт в каждом l oop объем виртуальной памяти никогда не уменьшался, как показано в cout из statex.ullAvailVirtual ???

Если я изменился динамическое c выделение памяти VirtualAlloc(), в каждом l oop я вижу размер виртуальной памяти, уменьшенный на 4 байта, что логично, поскольку размер страницы составляет 4 байта.

#include <Windows.h>
#include <iostream>

int main()
{
    unsigned int allocated = 0;

    while (true)
    {
        MEMORYSTATUSEX statex;

        statex.dwLength = sizeof(statex);

        GlobalMemoryStatusEx(&statex);

        //Depleting the memory per byte.
        char* dyn_mem = new char[1];
        *dyn_mem = 'a';


        std::cout << "There are " << statex.ullAvailVirtual / 1024 << " free  KB of virtual memory." << std::endl;
    }
    return 0;
}

1 Ответ

1 голос
/ 06 апреля 2020

То, что вы видите, - это оптимизация выделения памяти. См. этот ответ для более подробной информации о том, как работают распределение и освобождение. По сути, очень неэффективно выделять каждый байт за раз из ОС (или, возможно, вообще невозможно), потому что он обычно обрабатывает память в страницах (в моей системе 4 КБ), а не в отдельных байтах.

Поставщики компиляторов для ваша платформа (в данном случае Microsoft, если вы используете msv c) очень хорошо это знает и реализует низкоуровневые выделения памяти таким образом, чтобы они обрабатывали выделения подстраниц. malloc например, может выделить одну страницу памяти при запуске приложения. При запуске программе может не потребоваться столько памяти, поэтому mallo c отслеживает, что она запрашивала у ОС и что приложение запрашивало у mallo c. Если у mallo c не хватает места, он запрашивает другую страницу у ОС.

Стандартный контейнер библиотеки (например, std::vector) работает очень похожим образом (см. std::vector::resize и std::vector::reserve).

Если вы увеличите свое распределение до 10 байт за итерацию (вместо 1), вы увидите, что память меняется довольно быстро. В моем случае вы можете видеть, как происходит переход:

There are 137434705464 free  KB of virtual memory.
There are 137434705464 free  KB of virtual memory.
There are 137434705464 free  KB of virtual memory.
There are 137434701368 free  KB of virtual memory.
There are 137434701368 free  KB of virtual memory.
There are 137434701368 free  KB of virtual memory.

Вы можете видеть, что есть одно изменение 4096 байт, которое соответствует размеру страницы в моей системе. В этот момент mallo c (или какая-либо другая функция выделения) исчерпала зарезервированную память и запросила новый блок.

Обратите внимание, что я использовал malloc здесь как заполнитель для любой обычной функции выделения памяти.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...