2010-03-09 6 views
4

У меня есть следующий сценарий 186.py:программа Python не выйдет после завершения

S=[] 
study=set([524287]) 

tmax=10**7 
D={} 
DF={} 
dudcount=0 
callcount=0 

def matchval(t1,t2): 
    if t1==t2: 
     global dudcount 
     dudcount+=1 
    else: 
     global callcount 
     callcount+=1 
     D.setdefault(t1,set([])) 
     D.setdefault(t2,set([])) 
     D[t1].add(t2) 
     if t1 in D[t2]: 
      DF.setdefault(t1,set([])) 
      DF[t1].add(t2) 
      DF.setdefault(t2,set([])) 
      DF[t2].add(t1) 

for k in xrange(27): 
    t1=(100003 - 200003*(2*k+1) + 300007*(2*k+1)**3)%(1000000) 
    S.append(t1) 
    t2=(100003 - 200003*(2*k+2) + 300007*(2*k+2)**3)%(1000000) 
    S.append(t2) 
    matchval(t1,t2) 

t1=(100003 - 200003*(55) + 300007*(55)**3)%(1000000) 
S.append(t1) 
t2=(S[31]+S.pop(0))%(1000000) 
S.append(t2) 
matchval(t1,t2) 

for k in xrange(29,tmax+1): 
    t1=(S[31]+S.pop(0))%(1000000) 
    S.append(t1) 

    t2=(S[31]+S.pop(0))%(1000000) 
    S.append(t2) 
    matchval(t1,t2) 

D.setdefault(524287,set([])) 
DF.setdefault(524287,set([])) 
print D[524287] 
print DF[524287] 
print dudcount,callcount 
print "Done" 

последняя строка выводит «Done», но питон не выходит, когда это произойдет. Я введите следующую команду:

$ time python 186.py 

И получить результаты:

set([810528L, 582178L, 49419L, 214483L, 974071L, 651738L, 199163L, 193791L]) 
set([]) 
11 9999989 
Done 

Но я должен Ctrl + C, чтобы получить время:

real 34m18.642s 
user 2m26.465s 
sys  0m11.645s 

После результатов программы «Done «Использование процессора python очень мало ... но использование памяти продолжает расти ... Я использовал ctrl + C, когда получил до 80% моей системной памяти (ее старая система).

Что здесь происходит? Что делает программа после создания Done? Разве это не должно быть сделано?

Спасибо, Dan

ответ

5

я запускал тот же самый код на моем 2 ГГц двухъядерный ноутбук с 2 Гб оперативной памяти, и она занимает около 1 1/2 минут в Cygwin. Использование памяти увеличилось более чем на 600 МБ до того, как программа завершилась, и потребовалось около 2-4 секунд после появления Done, чтобы появилось приглашение и память была выпущена. Однако после появления Done я не видел увеличения памяти.

Я предполагаю, что это связано с управлением памятью. После появления Done Python работает над освобождением всей памяти, которая может занять довольно долгое время на более старой машине с меньшим объемом оперативной памяти. Я не уверен, почему память действительно увеличивается, если только не задержка в том, что говорит вам, сколько памяти используется.

+0

+1 освобождение памяти - что я только что написал ... –

+0

Ну, у меня только 480 МБ ОЗУ. 1,4 ГБ SWAP. По-прежнему кажется странным, что для очистки памяти потребуется 10 раз больше, чем фактически запустить программу. Может ли тот факт, что я обмениваюсь (и вы, вероятно, нет), объясняет, почему процесс освобождения памяти занимает больше времени, чем сама программа? – Dan

+0

Выполнение некоторых дополнительных испытаний ... Эта проблема применяется только при обмене данными. Я начинаю думать, что это не проблема с кодом/python, а проблема с системой с скоростями записи на жестком диске или что-то в этом роде ... так что, вероятно, это уже не вопрос программирования. Спасибо за вашу помощь. – Dan

1

Нет указаний в том, что вы опубликовали, которые соответствуют описанным симптомам. Возможно, отступы в исполняемом коде заполнены, и вы действительно собираетесь запустить еще один цикл вокруг всей кучи. Обратите внимание, что только храбрые люди будут пытаться воспроизвести вашу проблему, когда ей нужно 34 минуты. Можете ли вы воспроизвести эту проблему за более короткое время?

Когда вы сделали Control-C, что сказал трассировка?

В любом случае, я настоятельно рекомендую не иметь жестко закодированных констант (?) По всему месту, например. 524287 .... дайте это значащее имя и сделайте meaningful_name = 524287 в начале. Или, если это действительно переменная, подайте ее через sys.argv.

+0

Программа не занимает 34 минуты. Для запуска требуется ~ 2 минуты, а затем не выходит. Я позволил ему продержаться еще 32 минуты, прежде чем принять решение убить его. Когда я уменьшаю значение tmax, он работает намного быстрее и не имеет такой же проблемы. – Dan

+0

Ох. Так что это было заменой, и вы (а) не заметили (б) заметили, но думали, что это не стоит упоминать? –

+0

было (а).Я до сих пор не совсем понимаю, как обкатка объясняет это странное поведение ... очистка свопов всегда должна идти быстрее, чем своп-запись, не так ли? Как очистка подкачки может на порядок превышать первоначальную программу? – Dan

Смежные вопросы