views:

96

answers:

7

Hello,

I'm working my way through some code examples and I stumbled upon this:

endings = ['st', 'nd', 'rd'] + 17 * ['th'] + ['st', 'nd', 'rd'] + 7 * ['th']
+ ['st']

I understand that for numbers after 4 and until 20 they end in 'th' and I can see that we are adding 17 more items to the list, and I understand that '17 * ['th'] is adding 'th' to the list 17 times, however, I don't understand how this works.

Can you shed some light on this?

A: 

Consider twentieth twenty first twenty second twenty third ... thirtieth thirty first

Or is it something else that you don't understand about it?

Colin Fine
CrazyJuggler, nailed what I wasn't understanding. The * operator is creating a whole new list and then adding it to the previous list.
NoahClark
+4  A: 

17 * ['th'] generates ['th', 'th', ..., 'th'] (17 items).

In addition it's worth noting 2 behaviours:

  • That this is only really useful because the contents 'th' is immutable (unless of course you never intended to modify the ending list).
  • The list object ['th'] is only created once, however it is extended by iterating over the original copy 17 times, appending each entry to the final ['th', ...] list. This in turn is merged with the surrounding endings via the + operator.

I don't normally shed my light. Only about once every 6 months. If you see it lying about don't tell anyone it's mine.

Matt Joiner
+2  A: 

The + operator returns the 'sum' of 2 list, or both of them concatenated together. The * operator returns a list added to itself X times.

http://www.linuxtopia.org/online_books/programming_books/python_programming/python_ch14s03.html

CrazyJugglerDrummer
+1  A: 

The part of the code 17 * ['th'] creates a list with 17 items that are all 'th' and the + operator concatenates the list together, so ['st', 'nd', 'rd'] + 17 * ['th'] would become ['st', 'nd', 'rd', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th', 'th']

murgatroid99
+2  A: 

When multiplying a list, you're creating a new list containing the elements of the list that many times. In this case, 17 * ['th'] creates a list containing seventeen strings 'th'. When adding lists together, you're creating a new list containing the elements of all operands.

>>> a = [1, 2]
>>> a * 2
[1, 2, 1, 2]

>>> a = ['th']
>>> b = ['st']
>>> 3 * a + b
['th', 'th', 'th', 'st']
Ivo
+1  A: 

That makes the following list:

endings = [ "st", "nd", "rd", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "th", "st", "nd", "rd", "th", "th", "th", "th", "th", "th", "th" ]

So if you want to write "21st", do

"{0}{1}".format( 21, endings[ 20 ] )

Notice that the list is off by one, since endings[0] is the first element.

katrielalex
`ordinal = lambda x: str(x) + endings[x - 1]`, valid for 0 < x < 32.
Mike DeSimone
A: 

Additionally, you can override the operators of your own objects e.g.

#!/usr/bin/env python
# encoding: utf-8

class SomeClass(object):
    def __init__(self, v):
        self.value = v

    def __add__(self, b):
        return self.value + b.value

def main():
    a = SomeClass(1)
    b = SomeClass(2)
    print a + b


if __name__ == '__main__':
    main()

see http://docs.python.org/library/operator.html for more details

Matt Williamson