[Tutor] Please look at my wordFrequency.py
Kent Johnson
kent37 at tds.net
Tue Oct 11 19:37:44 CEST 2005
Kent Johnson wrote:
> Dick Moores wrote:
>
>> Kent Johnson wrote at 03:24 10/11/2005:
>>
>>> Dick Moores wrote:
>>>
>>>> (Execution took about 30 sec. with my computer.)
>>>
>>>
>>> That's way too long
>>
>>
>>
>> How long would you expect? I've already made some changes but haven't
>> seen the time change much.
>
>
> A couple of seconds at most, unless you are running it on some dog
> computer. It's just not that much text and you should be able to process
> it in a couple of passes at most.
OK I couldn't resist. I took your program and ran it on my computer - took about 38 seconds and got the same results as you. Then I made the changes I outlined, and a few other similar ones, and got it down to 34 secs. Finally I made the change suggested by John Fouhy - to accumulate the counts in a dict - and the time went down to 0.23 seconds.
>> Also, I'm puzzled that whether or not psyco is employed makes no
>> difference in the time. Can you explain why?
>
>
> My guess is it's because you have so many O(n^2) elements in the code.
> You have to get your algorithm to be O(n).
In particular this code:
for word in L:
k = L.count(word)
if (k,word) not in F:
F.append((k,word))
L.count() has to scan through the entire list (L) looking for a match with each word. So for each word, you are making 26140 string compares. The total number of compares is 26140*26140 or 683,299,600. That's a lot!
Then, for each word, you scan F for a match. Now you are doing tuple compares. The number of compares will increase as the length of F, but overall it will be about 26140*3700/2 or 48,359,000 compares.
Compare this to the dictionary version which just iterates L once, doing a dictionary lookup and write for each word.
The reason psyco doesn't make much difference is because all the time is spent in list.count() which is already C code.
Kent
More information about the Tutor
mailing list