新的一维数组非常大,如60000 * 60000

时间:2019-06-27 03:01:32

标签: c++ arrays

语言:C ++
系统:Windows 7 x64
内存:8GB RAM

我想在我的64位应用程序中新建一个大的一维数组,其中包含60000 * 60000 = 3600000000无符号的短类型元素。
目的是读取一张非常大的60k * 60k像素的图片,并将其转换为一维数组以进行进一步处理。我当然可以拆分图片并单独阅读,但是在生产环境中,确实有128GB和更多的RAM需要消耗。

1。静态方法

unsigned short array [3600000000]; 它显示 错误:数组'a'的大小为负数

2.malloc方法:

unsigned long long bytes = 3600000000 * sizeof(unsigned short);  
unsigned short *arr;  
arr = (unsigned short *)malloc(bytes);//almost 6.7GB memory

在具有8GB RAM的PC中,在malloc行调试时arr的地址为0x0
在其他具有16GB RAM的PC中,arr的地址有效,但是如果我将值分配给arr中的每个项目,例如

#include <iostream>
#include <string.h>
using namespace std;
int main()
{
    unsigned short *arr;
    arr = (unsigned short *)malloc(3600000000 * sizeof(unsigned short));//memory space can be allocate to arr, about 6.7GB
    if (arr == NULL){
        cout << "failed"<< endl;
    }
    memset(arr, 1, sizeof(arr));
    cout << arr << endl;
}

在某些奇怪的内存位置处会发生中断,arr为0x11103630A52B112。
在具有8GB RAM的PC x64中,它显示“失败”
在具有16GB RAM的其他PC x64中,arr的地址有效,但是如果我使用for循环为arr中的每个项目分配值,则将在某些有线存储位置发生中断arr为0x11103630A52B112
我怎么能新建一个非常大的一维数组

1.(静态方法8GB)它显示 错误:数组'a'的大小为负
2.(malloc方法为8GB)error log with my 8GB and memset statement

oneDimensionalArray.cpp: In function 'int main()':
oneDimensionalArray.cpp:10:47: warning: unsigned conversion from 'long long int' to 'size_t' {aka 'unsigned int'} changes value from '7200000000' to '2905032704' [-Woverflow]
     arr = (unsigned short *)malloc(3600000000 * sizeof(unsigned short));//memory space can be allocate to arr, about 6.7GB
                                    ~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~
oneDimensionalArray.cpp:10:35: warning: argument 1 value '2905032704' exceeds maximum object size 2147483647 [-Walloc-size-larger-than=]
     arr = (unsigned short *)malloc(3600000000 * sizeof(unsigned short));//memory space can be allocate to arr, about 6.7GB
                             ~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
In file included from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\cstdlib:75,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\ext\string_conversions.h:41,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\bits\basic_string.h:6391,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\string:52,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\bits\locale_classes.h:40,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\bits\ios_base.h:41,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\ios:42,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\ostream:38,
                 from folderPath\mingw\installed\lib\gcc\mingw32\8.2.0\include\c++\iostream:39,
                 from oneDimensionalArray.cpp:1:
folderPath\mingw\installed\include\stdlib.h:503:40: note: in a call to allocation function 'void* malloc(size_t)' declared here
 _CRTIMP __cdecl __MINGW_NOTHROW  void *malloc (size_t) __MINGW_ATTRIB_MALLOC;
                                        ^~~~~~
failed

3.(malloc方式为16GB) 引发了一个异常:写访问权限冲突,分配语句 arr [i] = 1时arr为0x11103630A52B112 for循环

2 个答案:

答案 0 :(得分:9)

您所在的行:

unsigned long long bytes = 3600000000 * sizeof(unsigned short);

对于分配的内存量,这看起来是正确的,但是您也可以使用相同的值来遍历数组:

for(long long i = 0; i<bytes;i++){
    arr[i] = 1;
}

这是错误的,数组中只有3600000000个元素,而不是3600000000 * sizeof(unsigned short)。您正在写超出分配的内存末尾的内容。

答案 1 :(得分:1)

除了@Blastfurnace关于使用太大索引的良好观察:

“其他具有16GB RAM的电脑,arr的地址有效”中可能存在溢出

如果size_t是32位,则malloc(bytes)会将大于bytes的{​​{1}}转换为比SIZE_MAX小得多的值。返回一个有效的指针,但不是所需的大小。

使用3600000000 * sizeof(unsigned short)代替unsigned long long bytes,启用所有警告并注意数学size_t bytes不会溢出。

3600000000 * sizeof(unsigned short)

  

读取一张非常大的图片,其大小为60k * 60k像素

要解决OP的更高问题,请为60k * 60k #if 3600000000 > SIZE_MAX/sizeof(unsigned short) #error overflow #endif size_t bytes = 3600000000 * sizeof(unsigned short); 数组分配3600000000 * sizeof(unsigned short)字节。

相反,为60k unsigned short个数组分配60k次。

(OP正在使用C ++,但似乎要使用unsigned shortmalloc()会更像C ++。)

new