[Tutor] Ingenious script (IMO)

Eric Brunson brunson at brunson.com
Mon Aug 6 17:40:37 CEST 2007


Dick Moores wrote:
> At 06:49 AM 8/6/2007, Kent Johnson wrote:
>   
>> Dick Moores wrote:
>>     
>>> http://www.rcblue.com/Python/changeMaker_revised_for_US_denominations.py
>>> I'm still working at Python--been at it a while--and thought the 
>>> script was ingenious. Do the Tutors agree? Or is it just 
>>> run-of-the-mill programming? Could it have been more simply written?
>>>       
>> I don't find it either ingenious or well-written. The algorithm is 
>> the same one you would use to count out an amount by hand so it 
>> doesn't seem so unusual. IMO the code relies too much on indices. If 
>> you rewrite it using a dict (or, even better, defaultdict(int)) for 
>> coinCount, there is no need for indices at all. Even with coinCount 
>> as a list, it could be better written.
>>
>> coinCount = []
>> for d in denominations:
>>     coinCount.append(0)
>>
>> =>
>>
>> coinCount = [0] * ndenominations
>>
>>
>> The main loop could be
>> for deno in range(ndenominations):
>>   if not remaining:
>>     break
>>
>> or
>> for i, deno in enumerate(denominations):
>> # i is now the index, deno is the actual denomination
>>
>>
>> but I would write it this way and avoid the use of the index completely:
>>
>>     
> >from collections import defaultdict
>   
>> coinCount = defaultdict(int)
>> remaining = change
>>
>> #   Loop until either we have given all the change or we have
>> #   run out of coin denominations to check.
>> for deno in denominations:
>>     if not remaining:
>>         break
>>
>>     #   For one denomination, count out coins of that denomination
>>     #   as long as the remaining amount is greater than the denomination
>>     #   amount.
>>
>>     while remaining >= deno:
>>         coinCount[deno] += 1
>>         print "remaining =", remaining
>>         remaining -= deno
>>
>> #   Report the results.
>> print "Your change is $%.02f"% (float(change) / CPD)
>> for deno in denominations:
>>     if coinCount[deno] > 0:
>>         if deno >= 100:
>>             print "$%d bills:\t" % (deno / CPD), coinCount[deno]
>>         else:
>>             print "%d-cent coins:\t" % (deno), coinCount[deno]
>>
>>
>> Kent
>>     
>
> Thanks Kent!
>
> Here's what I have after incorporating your suggestions:
>
> =================================
> #!/usr/bin/env python
> #coding=utf-8
> from collections import defaultdict
>
> CPD = 100
> cost = int(CPD * float(raw_input("Enter the cost: ")))
> tend = int(CPD * float(raw_input("Enter the tendered amount: ")))
>
> #   Calculate the change.
> change = tend - cost
>
> coinCount = defaultdict(int)
> print coinCount
> remaining = change
> denominations = (2000, 1000, 500, 100, 50, 25, 10, 5, 1)
>
> #   Loop until either we have given all the change or we have
> #   run out of coin denominations to check.
> for deno in denominations:
>      if not remaining:
>          break
>
>
>      #   For one denomination, count out coins of that denomination
>      #   as long as the remaining amount is greater than the denomination
>      #   amount.
>
>
>      while remaining >= deno:
>          coinCount[deno] += 1
>          remaining -= deno
>
>   

Try something like:

def makechange( amount, denominations ):

    coins = {}
    for d in denominations:
        coins[d] = int( amount/d )
        amount = amount%d

    return coins

> #   Report the results.
> print "Your change is $%.02f"% (float(change) / CPD)
> for deno in denominations:
>      if coinCount[deno] > 0:
>          if deno >= 100:
>              print "$%d bills:\t" % (deno / CPD), coinCount[deno]
>          else:
>              print "%d-cent coins:\t" % (deno), coinCount[deno]
> ========================================
>
> Gotta say though, I still don't understand how the defaultdict works here.
>
> Dick
>
>
>
> _______________________________________________
> Tutor maillist  -  Tutor at python.org
> http://mail.python.org/mailman/listinfo/tutor
>   



More information about the Tutor mailing list