The misunderstanding is due to poor documentation that doesn't catch a major change in specs, or due to the CPython implementation which dare to write a class for what is listed as a built-in function in the specs.
In Python 2, it is a function that returns a list. In the online documentation of Python 2, it is listed under Built-in Functions. The first line of help(map) on CPython 2.7.10 reads
Help on built-in function map in module builtin
correctly calling it a function.
In Python 3, they changed the specs that it returns an iterator instead of a list. As @RafaelC noted, it has an advantage of lazy loading. Althiugh it is still under "Built-n Functions", the CPython implementation decided to make it a class. This change is reflected in help(map), which you have seen and quoted in the question.
What you are doing when you call map() in CPython 3 is, you are creating an object of class map with the parameters you throw. This is clearly shown when you try to print what map() returns.
CPython 2.7.10:
>>> map(int, "12345")
[1, 2, 3, 4, 5]
CPython 3.7.2:
>>> map(int, "12345")
<map object at 0x1023454e0>
So you are clearly creating an object of class map, which makes what you've seen in help(map) sound very fine.
So it seems that, to the CPython core developers, a class can be a "function" with some definiton of a "function". This is clearly misleading. Anyway, it implements the necessary methods that enables it to be used as an iterator. (as the docs says, if you ignore that it's listed under builtin functions.)
It's used as a function
That's because the syntax of calling a function and fetching its return value is identical to creating a class object (by calling its initializer) and fetching the object.
For example, using a function my_function() as in return_value = my_function() is syntactically no different from creating a class object of my_class() as in my_object = my_class(). When you call map() in CPython 3, you are creating an object of class map. But you would write the same even if map were a function. That's why you're confused.
So in short,
mapwas a function in CPython 2, but is a class in CPython 3. That is clear fromhelp(map)on both versions, and that's what the CPython implementation does.The documentation keeps it under "Built-in functions" while CPython implementation finds liberty to write a class for it, causing confusion.
It's a shame that the two aren't clearly distinguished in the docs.
The term "mapping" is described in the Python glossary as:
A container object that supports arbitrary key lookups and implements the methods specified in the
MappingorMutableMappingabstract base classes. Examples includedict,collections.defaultdict,collections.OrderedDictandcollections.Counter.
The requirements to subclass collections.abc.Mapping are described in its docstring:
A Mapping is a generic container for associating key/value pairs.
This class provides concrete generic implementations of all methods except for
__getitem__,__iter__, and__len__.
So you can define a new mapping type by subclassing collections.abc.Mapping, and implementing three methods: __len__, __getitem__, and __iter__.
>>> from collections.abc import Mapping
>>> def func(**kwargs):
... print(kwargs)
...
>>> class MyMapping(Mapping):
... def __len__(self):
... return 1
... def __getitem__(self, k):
... return 'bananas'
... def __iter__(self):
... return iter(['custard'])
...
>>> func(**MyMapping())
{'custard': 'bananas'}
According to Python docs:
A container object that supports arbitrary key lookups and implements the methods specified in the Mapping or MutableMapping abstract base classes. Examples include:
- dict
- collections.defaultdict
- collections.OrderedDict
- collections.Counter.
The class is a mapping if it implements all methods from the Mapping / MutableMapping.
If you will create a Mapping/MutableMapping derived class and implement all of this, you will get a class that is a mapping.
Videos
newList = map(method, objectList) would call method(object) on each object in objectlist.
The way to do this with map would require a lambda function, e.g.:
map(lambda obj: obj.method(), objectlist)
A list comprehension might be marginally faster, seeing as you wouldn't need a lambda, which has some overhead (discussed a bit here).
Use operator.methodcaller():
from operator import methodcaller
map(methodcaller('methodname'), object_list)
This works for any list of objects that all have the same method (by name); it doesn't matter if there are different types in the list.