jovan 发表于 2015-12-5 18:53:18

自定义类型的内存占用巨大

想要定义一个数据类型,希望能中间包含一个可变大小的数组,写了代码如下
type cell
integer :: fn
integer, dimension(:), allocatable ::nd
end type cell
type(cell), dimension(:), allocatable ::elem
allocate(elem(10000))

只是给结构体elem赋了内存,维数10000,没有给nd赋内存,但是在进程管理器里查看已经占用了几十倍于10000*4字节的内存,而且再给nd赋内存并赋值后,内存进一步增加。
原以为自定义结构体中不能包含可变大小的数组,于是修改代码为:type cell
integer :: fn
integer, dimension(:), pointer ::nd
end type cell
type(cell), dimension(:), allocatable ::elem
allocate(elem(10000))
这样给结构体elem赋内存后,内存占用无异常,但当每一个指针elem(i)%nd指向一个大小不同的数组后,内存占用出现了同样的问题,占用了几十倍于指向的数组的大小,请问如何解决?谢谢

pasuka 发表于 2015-12-5 18:58:57

完整的代码?
操作系统?
编译器?
编译参数?
啥也没有的话,就算盖茨也没辙

jovan 发表于 2015-12-5 19:43:39

本帖最后由 jovan 于 2015-12-5 19:45 编辑

操作系统是:Win7编译器:Intel Visual Studio2010
编译环境:x64 Release
完整代码太长了,没法贴,我在一些可疑的地方赋内存之后pause,发现这个结构体一赋内存,内存占用就狂飙

fcode 发表于 2015-12-5 20:24:00

楼主的问题已在QQ群讨论解决:
1.楼主使用的64位编译器,一个地址占8字节,而非楼主计算的4字节
2.由于Fortran的可分配数组(指针同),除了记录数组的首地址(8字节)之外,还记录数组的维度,每个维度的上限 / 下限 / 间距。因此,这些结构(或称数组描述符 descriptor ) 占用约32字节

pasuka 发表于 2015-12-5 20:44:45

fcode 发表于 2015-12-5 20:24
楼主的问题已在QQ群讨论解决:
1.楼主使用的64位编译器,一个地址占8字节,而非楼主计算的4字节
2.由于Fort ...

既然如此,还不如在C里面定义这个结构体及其相关操作,然后ISO C BINDING做个interface
有些譬如链表、哈希表啥的,Fortran真的不如C方便与高效

fcode 发表于 2015-12-5 22:59:17

如果把变量和结构都写入 C 定义,那么相关的计算也必须写入 C,因为可分配数组和fortran指针,都是特殊的数据结构。
fortran的指针包含更丰富的内容,以至于它更安全,不容易越界或指向数组之外。当然,它是以牺牲内存为代价的。
通常来说,较大的数组,但数组个数不多,那么牺牲一点内存来存储这些额外的信息(维度/上下限)是值得的。

像楼主这种1800万个可分配数组,毕竟是较少的情况。

pasuka 发表于 2015-12-6 09:37:21

fcode 发表于 2015-12-5 22:59
如果把变量和结构都写入 C 定义,那么相关的计算也必须写入 C,因为可分配数组和fortran指针,都是特殊的数 ...

长度是1800w的话,为啥不考虑上SQL数据库或者Hadoop这类大数据处理平台,再不济的话,也得整个out-of-core的模式
直接囫囵吞枣往计算机内存塞那么多信息,实在是费力不讨好的,譬如高清视频动辄20、30G,远超过内存容量,但是播放的时候,只会读入一段数据
lz应该去看看数据库以及大数据处理相关的现成软件包或框架

jovan 发表于 2015-12-6 10:08:54

pasuka 发表于 2015-12-6 09:37
长度是1800w的话,为啥不考虑上SQL数据库或者Hadoop这类大数据处理平台,再不济的话,也得整个out-of-cor ...

这个是流体计算网格的前处理程序,以前处理小网格没有啥问题,现在算大网格出了这问题,回头我换个平台试试看,要还是不行就考虑改程序,数据库完全不懂...

fcode 发表于 2015-12-6 10:11:35

从数据库取数,必然比从内存取数会慢很多

时间(执行效率)和空间(内存大小)总是不可兼得,两难相权取其轻吧。

pasuka 发表于 2015-12-6 10:14:46

jovan 发表于 2015-12-6 10:08
这个是流体计算网格的前处理程序,以前处理小网格没有啥问题,现在算大网格出了这问题,回头我换个平台试 ...

CFD计算的话,不妨去OpenFoam的论坛或者mailing-list去问问看,肯定有成熟的解决办法
页: [1] 2
查看完整版本: 自定义类型的内存占用巨大