BAT面試題——海量整數,找出不重複整數

歡迎關注,敬請點贊!
海量數據
海量數據時代,不是誰都可以一口悶。
海量

題目:在2.5億個整數中,找出不重複的整數(注,內存不足以容納這2.5億個整數)。

構建測試數據

返回頂部

# 構建一個測試數據集:隨機生成10000個(-20000, 20000)的整數,以字符串格式存入bigdata中
import random


for i in range(10000):
    with open('bigdata', 'a') as file:
        file.write(str(random.randint(-20000, 20000)) + '\n')

方法一(內存充足):用python字典結構:

返回頂部
在內存充足的情況下,使用python中的字典結構。
對2.5億個數中的每一個數,出現一次,字典對應的值+1。
最後遍歷字典,找出value爲1的所有key。

int_dict = {}  # 整數字典,整數爲key,次數爲value
def dict_int():
    with open('bigdata') as file:
        for str_in in file:
            num = str_in.replace('\n', '')
            if num not in int_dict:  # 第一次出現
                int_dict[num] = 1
            else:
                int_dict[num] += 1

    with open('bigdata') as file:
        for str_in in file:
            num = str_in.replace('\n', '')
            if int_dict[num] == 1:  # 返回一個不重複整數的迭代器
                yield num

if __name__ == '__main__':
    unique_list = list(dict_int())
    print('不重複整數個數:', len(unique_list))
不重複整數個數: 7875

前10個不重複整數

print('前10個不重複整數:', unique_list[:10])
前10個不重複整數: [-3421, -1349, -6778, 16932, 14847, -1504, 15398, 12612, -8009, -1250]

方法二(內存不足):用bool數組:

返回頂部
初始化一個(2.5*10^8) * 2 bool數組,並且初始化爲False,對於每一個整數。
使用兩個bit,來表示它出現的次數:
0 0:出現0次
0 1:出現一次
1 1:出現多次

import numpy as np


mark =np.zeros((25*(10**7), 2), dtype=np.bool)

存放(2.5*10^8) * 2 bool數組,需要0.47 G 內存

print('(2.5*10^8) * 2 bool數組的大小:',round(mark.size/1024**3, 2), 'G內存')
(2.5*10^8) * 2 bool數組的大小: 0.47 G內存
def get_unique_int():
    with open('bigdata') as file:  # bigdata:原始的2.5億個整數大文件
        for str_in in file:
            num = int(str_in)
            if mark[num][0] == False and mark[num][1] == False:  # 這個數第一次出現。賦值 0 1
                mark[num][0] = False
                mark[num][1] = True
            else:
                mark[num][0] = True                              # 出現了不止一次的數據,賦值 1 1
                mark[num][1] = True

    with open('bigdata') as file:
        for str_in in file:
            num = int(str_in)
            if mark[num][0] == False and mark[num][1] == True:  # 判斷只出現一次,即值爲 0 1
                yield num


if __name__ == '__main__':
    unique_list = list(get_unique_int())
    print('不重複整數個數:', len(unique_list))
不重複整數個數: 7875

前10個不重複整數

print('前10個不重複整數:', unique_list[:10])
前10個不重複整數: [-3421, -1349, -6778, 16932, 14847, -1504, 15398, 12612, -8009, -1250]

總結:

兩種思路殊途同歸,用字典結構可能存不下2.5億個結果;用bool數組,只需要0.5 G 左右的內存。

歡迎關注,敬請點贊!
返回頂部

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章