2016-02-21 16 views
10

Giả sử rằng các máy tính chạy chương trình này có một số lượng vô hạn của bộ nhớ, Tôi quan tâm đến nơi Python sẽ phá vỡ khi chạy như sau:Những giới hạn kỹ thuật nào ngăn cản việc tính số Graham trong python?

Đối với niềm vui, tôi thực hiện hyperoperators trong python như module hyperop. Một trong những ví dụ của tôi là số Graham:

def GrahamsNumber(): 
    # This may take awhile... 
    g = 4 
    for n in range(1,64+1): 
     g = hyperop(g+2)(3,3) 
    return g 

Phiên bản đặc của lớp hyperop trông như thế này:

def __init__(self, n): 
    self.n = n 
    self.lower = hyperop(n - 1) 

def _repeat(self, a, b): 
    if self.n == 1: 
     yield a 

    i = 1 
    while True: 
     yield a 
     if i == b: 
      break 
     i += 1 

def __call__(self, a, b): 
    return reduce(lambda x, y: self.lower(y, x), self._repeat(a, b)) 

Về cơ bản thư viện chỉ là một hoạt động lần bên phải đệ quy, với một định nghĩa đặc biệt đối với số base case of n=1. Ban đầu __call__ được đánh gôn đẹp như:

return reduce(lambda x, y: self.lower(y, x), [a,]*b) 

Tuy nhiên, it turns out that you can't make a list with more elements than the size of a C long. Đó là một hạn chế thú vị mà hầu hết các lập trình viên Python có thể không gặp phải trong ngày bình thường của họ và nó đã truyền cảm hứng cho câu hỏi sau đây.

ở đâu, nếu ở tất cả, việc tính toán hyperop sẽ thất bại do một giới hạn kỹ thuật của python (đặc biệt 2.7.10)?

+5

Như * "vũ trụ có thể quan sát quá nhỏ để chứa một đại diện số thông thường của số của Graham" *, tôi sẽ nói không. Mẹo hàng đầu: nếu bạn phải bắt đầu với * "đây là câu hỏi hợp pháp" * có thể bạn đã sai! – jonrsharpe

+0

Có phải câu hỏi về việc sử dụng 'chuỗi sản lượng' và" chuỗi vô hạn "hay thứ gì đó có thể được ghim gọn gàng hơn không? – user2864740

+0

Giới hạn của nhiều phần tử hơn kích thước của C dài chỉ được đề cập cho Python 2 .... – PascalVKooten

Trả lời

1

phiên bản Có lẽ ban đầu của hyperop là mạnh mẽ và thất bại vì một số nguyên nhân bí truyền nhưng mã này chính xác không vì constructor hyperop gọi chính nó và nó làm tăng RuntimeError với "chiều sâu đệ quy tối đa vượt quá" (sau khi sys.setrecursionlimit các cuộc gọi đệ quy - có thể là 1000 trong 2.7.10 theo mặc định).

Các vấn đề liên quan