0

Suppose I have a list called a =['apple' 'anachi', 'butter' 'bread', 'cat' , 'catre']

I need to return elements as follows:

a['a'] should return [apple, anachi]
a['b'] should return ['butter', 'bread']

How do I do this in python

5
  • you need to make a function, based on input iterate over loop and whatsoever matches the first value, keep adding that in the array and return that array Commented Mar 20, 2015 at 6:17
  • It looks like you're missing some commas in your list, or are you trying to do something like nested lists? Commented Mar 20, 2015 at 6:18
  • Do you still need to access a by index too, or only by the first letters? Commented Mar 20, 2015 at 6:19
  • Show what you've tried and why it didn't work Commented Mar 20, 2015 at 6:21
  • @wim is there a inbuilt function in python to do it? Commented Mar 20, 2015 at 6:22

4 Answers 4

4

If you only want to access your list of names a by the first character and don't mind that it won't be a list anymore I have the following solution for you:

>>> from collections import defaultdict
>>> a =['apple', 'anachi', 'butter', 'bread', 'cat' , 'catre']
>>> d=defaultdict(list)
>>> for s in a:
    d[s[0]].append(s)


>>> a=d
>>> a['a']
['apple', 'anachi']
>>> a['b']
['butter', 'bread']
Sign up to request clarification or add additional context in comments.

Comments

1

You have a lot of options here.

First, note the behavior of your list currently:

a =['apple' 'anachi', 'butter' 'bread', 'cat' , 'catre']
print a[0]  # appleanachi
print a[1]  # butterbread

Since you're missing commas between "apple" and "anachi", and "butter" and "bread", they're being concatenated. I'm not sure that's what you want.

If you correct that to make it a "flat" list, you could extract elements from the list with the slicing syntax, but you would need to know the indices to do this:

a = ['apple', 'anachi', 'butter', 'bread', 'cat' , 'catre']
print a[0:2]  # ['apple', 'anachi']
print a[2:4]  # ['butter', 'bread']

Alternatively, you could use nested lists, then you wouldn't need the slicing syntax, just a single index of the "pair":

a = [['apple', 'anachi'], ['butter', 'bread'], ['cat' , 'catre']]
print a[0]  # ['apple', 'anachi']
print a[1]  # ['butter', 'bread']

All of these approaches so far required that you knew the index, but if you don't, and you want to extract elements from the list that have a certain prefix/start with a certain letter combination, you could do something like:

def search(lst, pre):
    return [e for e in lst if e.startswith(pre)]

a = ['apple', 'anachi', 'butter', 'bread', 'cat' , 'catre']
print search(a, 'a')  # ['apple', 'anachi']
print search(a, 'b')  # ['butter', 'bread']

This search approach could also be implemented for a nested list as well, for example if you wanted to find all the "pairs" where the first item of the pair started with the given prefix:

def search(lst, pre):
    return [p for p in lst if p[0].startswith(pre)]

a = [['apple', 'anachi'], ['butter', 'bread'], ['cat' , 'catre']]
print search(a, 'a')  # [['apple', 'anachi']]
print search(a, 'b')  # [['butter', 'bread']]

Comments

0

What I would do is implement a custom sequence:

from collections import Sequence

class MyList(Sequence):

    def __init__(self, data=()):
        super(MyList, self).__init__()
        self._list = list(data)

    def __getitem__(self, key):
        if type(key) == int:
            return self._list[key]
        return [e for e in self._list if e.startswith(key)]

    def __len__(self):
        return len(self._list)


a = MyList(['apple', 'anachi', 'butter', 'bread', 'cat' , 'catre'])

print a['a']  # prints ['apple', 'anachi']
print a['b']  # prints ['butter', 'bread']
print a['ca']  # prints ['cat' , 'catre']

Here the crucial part is the custom __getitem__, where instead of simply returning the item from the underlying list self._list, we return a new list of items from self._list that start with the given key.

Note that the code above has no error handling (for example you need to check that the elements are only strings for this to work).

1 Comment

you should handle integers in your __getitem__ otherwise normal list access will be broken
0

Using itertools.groupby:

>>> my_dict = {}
>>> for x,y in itertools.groupby(a, key=lambda x:x[0]):
...     my_dict[x] = my_dict.get(x,[]) + list(y)
...
>>> my_dict['a']
['apple', 'anachi']
>>> my_dict['b']
['butter', 'bread']
>>> my_dict['c']
['cat', 'catre']

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.