gpt4 book ai didi

python - 为什么 python 实现使用的内存比 C 多 9 倍?

转载 作者:太空狗 更新时间:2023-10-30 01:10:55 24 4
gpt4 key购买 nike

我编写了一个程序,用于在 Python 和 C 中列出从 2 到用户给定数字的素数。我运行了这两个程序来寻找相​​同数字的素数,并在事件监视器中查看了它们各自的进程。我发现 python 实现使用的内存正好是 C 实现的 9 倍。为什么 python 需要这么多的内存,为什么特定的倍数来存储相同的整数数组?以下是该程序的两个实现:

Python 版本:

import math
import sys

top = int(input('Please enter the highest number you would like to have checked: '))
num = 3
prime_list = [2]
while num <= top:
n = 0
prime = True
while int(prime_list[n]) <= math.sqrt(num):
if num % prime_list[n] == 0:
prime = False
n = 0
break
n = n + 1
if prime == True:
prime_list.append(num)
prime = False
num = num + 1
print("I found ", len(prime_list), " primes")
print("The largest prime I found was ", prime_list[-1])

C 版:

#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <sys/types.h>
#include <unistd.h>

int main(){
int N;
int arraySize = 1;
int *primes = malloc(100*sizeof(int));
int isPrime = 1;
primes[0] = 2;
int timesRealloc = 0;
int availableSlots = 100;

printf("Please enter the largest number you want checked: \n");
scanf("%d", &N);

int j = 0;
int i;
for (i = 3; i <= N; i+=2){
j = 0;
isPrime = 1;
while (primes[j] <= sqrt(i)) {
if (i%primes[j] == 0) {
isPrime = 0;
break;
}
j++;
}
if (isPrime == 1){
primes[arraySize] = i;
arraySize++;
}
if (availableSlots == arraySize){
timesRealloc++;
availableSlots += 100;
primes = realloc(primes, availableSlots*sizeof(int));
}
}

printf("I found %d primes\n", arraySize);
printf("Memory was reallocated %d times\n", timesRealloc);
printf("The largest prime I found was %d\n", primes[(arraySize-1)]);


return 0;
}

最佳答案

>>> import sys
>>> sys.getsizeof(123456)
28

这是 C int 大小的 7 倍。在 Python 3 中,整数是 struct _longobject 又名 PyLong 的实例:

struct _longobject {
PyVarObject ob_base;
digit ob_digit[1];
};

PyVarObject

typedef struct {
PyObject ob_base;
Py_ssize_t ob_size;
} PyVarObject;

PyObject

typedef struct _object {
Py_ssize_t ob_refcnt;
struct _typeobject *ob_type;
} PyObject;

从中我们得到对象 123456 在 64 位 Python 构建中的以下内存使用情况:

  • 8 个字节用于引用计数器 (Py_ssize_t)
  • 8 个字节用于指向类型对象 &PyLong_Type 的指针(类型为 PyTypeObject *
  • 8个字节,用于统计对象变长部分的字节数; (属于 Py_ssize_t 类型)
  • 整数中每30位数字4个字节。

由于 123456 适合前 30 位,因此总计为 28,或 7 * sizeof (int)

除了 Python list 中的每个元素都是指向实际对象的 PyObject * 之外;这些指针中的每一个在 64 位 Python 构建中都是 64 位;这意味着每个列表元素引用单独消耗的内存是 C int 的两倍。

将 7 和 2 相加得到 9


对于存储效率更高的代码,您可以使用 arrays ;使用类型代码 'i' 时,内存消耗应该非常接近 C 版本。 arrays 有 append 方法,多亏了它,增长数组应该比在 C 中更容易/使用 realloc

关于python - 为什么 python 实现使用的内存比 C 多 9 倍?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55367167/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com