Прежде всего, вы не говорите, в какой архитектуре вы пробуете этот подход. Во-вторых, вы не говорите, какую операционную систему вы используете. Вы только говорите, что пытаетесь malloc(3)
массив из одного миллиарда int
с.
Подумайте дважды: один массив из 1 000 0000 001 int
элементов имеет размер 4 000 000 004. Если вы пытаетесь обработать это в 32-битной архитектуре, вы просите систему выделить все пространство виртуальной памяти (которая составляет 4 ГБ) только для вашего массива. Скорее всего, у вас очень жесткий лимит, который мешает вам выделять такой объем памяти.
В 64-битной архитектуре у вас достаточно адресов для обработки этого, но, опять же, возможно, ваша операционная система откажется создавать одно непрерывное отображение такого размера (или объем виртуальной памяти, которую ваша система может обрабатывать). Наиболее вероятным является то, что вы не сможете получить эту память. Я вижу, что вы запускаете это в windows (по пути, который вы используете для имени файла), поэтому, скорее всего, вы даже не сможете проверить, сколько памяти вы можете обработать для процесса.
Я проверил вашу программу в 64-битная архитектура FreeBSD, в которой у меня есть следующие ограничения (я должен признать, что я немного их подправил, чтобы справиться с вашей проблемой для моей учетной записи пользователя, поскольку обычному пользователю в многопользовательской системе никогда не предоставляются такие ограничения по умолчанию):
$ ulimit -a
number of pseudoterminals (-P) unlimited
socket buffer size (bytes, -b) unlimited
core file size (blocks, -c) unlimited
data seg size (kbytes, -d) 33554432
file size (blocks, -f) unlimited
max kqueues (-k) unlimited
max locked memory (kbytes, -l) unlimited
max memory size (kbytes, -m) unlimited
open files (-n) 230121
pipe size (512 bytes, -p) 1
stack size (kbytes, -s) 524288
cpu time (seconds, -t) unlimited
max user processes (-u) 12042
virtual memory (kbytes, -v) unlimited
swap size (kbytes, -w) unlimited
(как вы можете видеть, я имею максимальный предел размера сегмента данных в 33 Гб, поэтому, если я запросил массив из 10 миллиардов элементов, я потерпел неудачу и должен сказать, что это ограничение навязано ядром, я не могу поднять его - даже как root)
- Когда я это сделал, я получил
SIGSEGV
, потому что указатель файла, возвращенный fopen(3)
, дал NULL
(файл не существует, еще одна вещь, которую вы не проверяете в своей программе), поэтому программа была прервана по вызову fscanf(3)
. Примечание. Необходимо проверить возвращаемые значения вызовов на наличие ошибок. - После этого я смог запустить (и действительно выделить миллиардный массив --plus one-- elements). ) без каких-либо проблем. Программа FreeBSD запускается за 0,001 с от начала до конца, так как ей не нужно выделять всю эту память в одном блоке (действительно, ей не нужно выделять все, так как вы используете только первые 126 элементов массива, поэтому действительно, вы выделите только одну страницу такой памяти, 504 байта памяти.
$ pru
*****************************************
THIS WAS FRIEND CIRCLE QUERIES
*****************************************
numberOfHandshakings: 99885
persons[0]= 0
persons[1]= 0
persons[2]= 0
[...]
persons[123]= 0
persons[124]= 0
persons[125]= 0
persons[126]= 0
Затем я установил максимальный объем виртуальной памяти 4 Гб и повторил тест:
$ pru
*****************************************
THIS WAS FRIEND CIRCLE QUERIES
*****************************************
numberOfHandshakings: 99885
malloc failed: Cannot allocate memory
на этот раз результат ulimit -a
был:
$ ulimit -a
number of pseudoterminals (-P) unlimited
[... same as before ]
max user processes (-u) 12042
virtual memory (kbytes, -v) 4194304 <<<<<< 4Gb virtual memory.
swap size (kbytes, -w) unlimited
Ваша программа после внесенных в нее изменений, чтобы иметь возможность обрабатывать ошибки, возвращаемые вызовами fopen()
и malloc()
было:
#include <ctype.h>
#include <errno.h>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#define population 1000000000
int numberOfHandshaking;
int main(int argc, char **argv)
{
printf("*****************************************\n");
printf(" THIS WAS FRIEND CIRCLE QUERIES\n");
printf("*****************************************\n\n");
FILE *fPointer;
fPointer =
fopen("Ass13in.txt", /* I changed this, my apologies */
"r");
if (fPointer == NULL) {
printf("couldn't open file: %s\n", strerror(errno));
exit(1);
}
fscanf(fPointer, "%d", &numberOfHandshaking); // Reads the first line
printf("numberOfHandshakings: %d\n", numberOfHandshaking);
int *persons = malloc((population+1) * sizeof(int));
if (persons == NULL) {
printf("malloc failed: %s\n", strerror(errno));
exit(1);
}
for (int i=0; i<127; i++){
printf("persons[%d]= %d \n", i, persons[i]);
}
printf("\n\n\n");
return 0;
}
и все работает нормально !!:)
ПРИМЕЧАНИЕ:
В вашей программе вы #include
файлы, которые вам не нужны к. Это:
#include <ctype.h>
#include <math.h>
#include <time.h>