Python basics

Nikolay Koldunov

[email protected]

This is part of Python for Geosciences notes.

================

Variables

Python uses duck typing

Int

In [1]:
a = 10
In [2]:
a
Out[2]:
10
In [3]:
type(a)
Out[3]:
int

Float

In [4]:
z = 10.7
z
Out[4]:
10.7
In [5]:
type(z)
Out[5]:
float

String

In [6]:
b = '2'
b
Out[6]:
'2'

Some operations are not allowed on different types:

In [7]:
a+b
---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-7-ca730b97bf8a> in <module>
----> 1 a+b

TypeError: unsupported operand type(s) for +: 'int' and 'str'

But some of them are allowed:

In [8]:
a*b
Out[8]:
'2222222222'

Might be a source of confusion :)

String variables can be combined:

In [9]:
c = ' guys walk into a bar'
c
Out[9]:
' guys walk into a bar'
In [10]:
b+c
Out[10]:
'2 guys walk into a bar'

In order to include variable of another type in to string you have to convert it:

In [11]:
str(a)+c
Out[11]:
'10 guys walk into a bar'

Everything is an object

In IPython you can get the list of object's methods and attributes by typing dot and pressing TAB:

In [ ]:
c.

Methods are basically default functions that can be applied to our variable:

In [12]:
c.upper()
Out[12]:
' GUYS WALK INTO A BAR'
In [13]:
c.title()
Out[13]:
' Guys Walk Into A Bar'
In [14]:
c.count('a')
Out[14]:
3
In [15]:
c.find('into')
Out[15]:
11

If you need help on method in IPython type something like:

In [16]:
c.find?

Or open bracket and press SHIFT+TAB:

In [ ]:
c.find(

Int variable is also an object:

In [18]:
a.bit_length()
Out[18]:
4

Methods can be combined (kind of a pipeline)

In [19]:
c.title().count('a').bit_length()
Out[19]:
2

Lists

There are several other interesting variable types in Python, but the one we would need the most is the list.

In order to create list put coma separated values in square brackets:

In [20]:
l = [1,2,3,4,5]
l
Out[20]:
[1, 2, 3, 4, 5]

Sort of similar to Matlab variables, but not exactly.

Values in list can be any type:

In [21]:
l = ['one', 'two', 'three', 'four', 'five']
l
Out[21]:
['one', 'two', 'three', 'four', 'five']

Combined

In [22]:
l = ['one', 2, 'three', 4.0, 3+2]
l
Out[22]:
['one', 2, 'three', 4.0, 5]

Any type means ANY type:

In [23]:
l = ['one', 2, 'three', [1,2,3,4,5], 3+2]
l
Out[23]:
['one', 2, 'three', [1, 2, 3, 4, 5], 5]

You can access list values by index:

In [24]:
l[0]
Out[24]:
'one'

Oh, yes, indexing starts with zero, so for Matlab users the zero is the new one :) See discussion on the matter here.

In [25]:
l[1]
Out[25]:
2

Let's have a look at the 4th element of our list:

In [26]:
l[3]
Out[26]:
[1, 2, 3, 4, 5]

It's also a list, and its values can be accessed by indexes as well:

In [27]:
l[3][4]
Out[27]:
5

You also can acces multiple elements of the list using slices:

In [28]:
l
Out[28]:
['one', 2, 'three', [1, 2, 3, 4, 5], 5]
In [29]:
l[1:3]
Out[29]:
[2, 'three']

Slice will start with the first slice index and go up to but not including the second slice index.

In [30]:
l[3]
Out[30]:
[1, 2, 3, 4, 5]

Control Structures

For loop:

This loop will print all elements from the list l

In [31]:
l = ['one', 2, 'three', [1,2,3,4,5], 3+2]

for element in l:
    print(element)
one
2
three
[1, 2, 3, 4, 5]
5

Two interesting thins here. First: indentation, it's in the code, you must use it, otherwise code will not work:

In [32]:
for element in l:
print(element)
  File "<ipython-input-32-c5812f5beca3>", line 2
    print(element)
        ^
IndentationError: expected an indented block

Second - you can iterate through the elements of the list. There is an option to iterate through a bunch of numbers as we used to in Matlab:

In [33]:
for index in range(5):
    print(l[index])
one
2
three
[1, 2, 3, 4, 5]
5

where range is just generating a sequence of numbers:

In [34]:
list(range(5))
Out[34]:
[0, 1, 2, 3, 4]

Branches

We are not going to use branches in this notes, but this is how they look like just as another example of indentation use:

In [35]:
x = -1
if x > 0:
    print("Melting")
elif x == 0:
    print("Zero")
else:
    print("Freezing")
Freezing

Modules

Pure python does not do much. To do some specific tasks you need to import modules. Here I am going to demonstrate several ways to do so.

The most common one is to import complete library. In this example we import urllib2 - a library for opening URLs using a variety of protocols.

In [36]:
import requests

Here we get information from FESOM website site. Note how function get is called. We have to use name of the library, then dot, then name of the function from the library:

In [37]:
response = requests.get('http://fesom.de/')
response.headers
Out[37]:
{'Date': 'Tue, 28 Apr 2020 15:58:46 GMT', 'Server': 'Apache', 'Content-Language': 'en', 'Vary': 'Accept-Encoding', 'Content-Encoding': 'gzip', 'Cache-Control': 'max-age=0', 'Expires': 'Tue, 28 Apr 2020 15:58:46 GMT', 'X-UA-Compatible': 'IE=edge', 'X-Content-Type-Options': 'nosniff', 'Content-Length': '7375', 'Keep-Alive': 'timeout=3, max=500', 'Connection': 'Keep-Alive', 'Content-Type': 'text/html; charset=utf-8'}

Another option is to import it like this:

In [38]:
from requests import *

In this case all functions will be imported in to the name-space and you can use get directly, without typing the name of the library first:

In [39]:
response = get('http://fesom.de/')
response.headers
Out[39]:
{'Date': 'Tue, 28 Apr 2020 15:58:48 GMT', 'Server': 'Apache', 'Content-Language': 'en', 'Vary': 'Accept-Encoding', 'Content-Encoding': 'gzip', 'Cache-Control': 'max-age=0', 'Expires': 'Tue, 28 Apr 2020 15:58:48 GMT', 'X-UA-Compatible': 'IE=edge', 'X-Content-Type-Options': 'nosniff', 'Content-Length': '7375', 'Keep-Alive': 'timeout=3, max=500', 'Connection': 'Keep-Alive', 'Content-Type': 'text/html; charset=utf-8'}

But generally this is very bad idea and is not recomended, because your name-space is populated by things that you don't really need and it's hard to tell where the function comes from.

In [40]:
whos
Variable                    Type          Data/Info
---------------------------------------------------
ConnectTimeout              type          <class 'requests.exceptions.ConnectTimeout'>
ConnectionError             type          <class 'requests.exceptions.ConnectionError'>
DependencyWarning           type          <class 'urllib3.exceptions.DependencyWarning'>
FileModeWarning             type          <class 'requests.exceptions.FileModeWarning'>
HTTPError                   type          <class 'requests.exceptions.HTTPError'>
NullHandler                 type          <class 'logging.NullHandler'>
PreparedRequest             type          <class 'requests.models.PreparedRequest'>
ReadTimeout                 type          <class 'requests.exceptions.ReadTimeout'>
Request                     type          <class 'requests.models.Request'>
RequestException            type          <class 'requests.exceptions.RequestException'>
RequestsDependencyWarning   type          <class 'requests.exceptio<...>questsDependencyWarning'>
Response                    type          <class 'requests.models.Response'>
Session                     type          <class 'requests.sessions.Session'>
Timeout                     type          <class 'requests.exceptions.Timeout'>
TooManyRedirects            type          <class 'requests.exceptions.TooManyRedirects'>
URLRequired                 type          <class 'requests.exceptions.URLRequired'>
a                           int           10
adapters                    module        <module 'requests.adapter<...>es/requests/adapters.py'>
api                         module        <module 'requests.api' fr<...>ackages/requests/api.py'>
auth                        module        <module 'requests.auth' f<...>ckages/requests/auth.py'>
b                           str           2
c                           str            guys walk into a bar
certs                       module        <module 'requests.certs' <...>kages/requests/certs.py'>
chardet                     module        <module 'chardet' from '/<...>ges/chardet/__init__.py'>
check_compatibility         function      <function check_compatibility at 0x107e7f3b0>
codes                       LookupDict    <lookup 'status_codes'>
compat                      module        <module 'requests.compat'<...>ages/requests/compat.py'>
cookies                     module        <module 'requests.cookies<...>ges/requests/cookies.py'>
cryptography_version        str           2.9.2
delete                      function      <function delete at 0x108e7a050>
element                     int           5
exceptions                  module        <module 'requests.excepti<...>/requests/exceptions.py'>
get                         function      <function get at 0x108e565f0>
head                        function      <function head at 0x108e5b440>
hooks                       module        <module 'requests.hooks' <...>kages/requests/hooks.py'>
index                       int           4
l                           list          n=5
logging                     module        <module 'logging' from '/<...>3.7/logging/__init__.py'>
models                      module        <module 'requests.models'<...>ages/requests/models.py'>
options                     function      <function options at 0x108e5b560>
packages                    module        <module 'requests.package<...>es/requests/packages.py'>
patch                       function      <function patch at 0x108e76f80>
post                        function      <function post at 0x108e76e60>
put                         function      <function put at 0x108e76ef0>
pyopenssl                   module        <module 'urllib3.contrib.<...>b3/contrib/pyopenssl.py'>
request                     function      <function request at 0x108e09680>
requests                    module        <module 'requests' from '<...>es/requests/__init__.py'>
response                    Response      <Response [200]>
session                     function      <function session at 0x108e615f0>
sessions                    module        <module 'requests.session<...>es/requests/sessions.py'>
status_codes                module        <module 'requests.status_<...>equests/status_codes.py'>
structures                  module        <module 'requests.structu<...>/requests/structures.py'>
urllib3                     module        <module 'urllib3' from '/<...>ges/urllib3/__init__.py'>
utils                       module        <module 'requests.utils' <...>kages/requests/utils.py'>
warnings                    module        <module 'warnings' from '<...>b/python3.7/warnings.py'>
x                           int           -1
z                           float         10.7

You can import only function that you need:

In [41]:
from requests import get
In [42]:
response = get('http://fesom.de/')
response.headers
Out[42]:
{'Date': 'Tue, 28 Apr 2020 15:58:50 GMT', 'Server': 'Apache', 'Content-Language': 'en', 'Vary': 'Accept-Encoding', 'Content-Encoding': 'gzip', 'Cache-Control': 'max-age=0', 'Expires': 'Tue, 28 Apr 2020 15:58:50 GMT', 'X-UA-Compatible': 'IE=edge', 'X-Content-Type-Options': 'nosniff', 'Content-Length': '7375', 'Keep-Alive': 'timeout=3, max=500', 'Connection': 'Keep-Alive', 'Content-Type': 'text/html; charset=utf-8'}

Or import library as alias in order to avoid extensive typing:

In [43]:
import requests as rq
In [44]:
response = rq.get('http://fesom.de/')
response.headers
Out[44]:
{'Date': 'Tue, 28 Apr 2020 15:58:51 GMT', 'Server': 'Apache', 'Content-Language': 'en', 'Vary': 'Accept-Encoding', 'Content-Encoding': 'gzip', 'Cache-Control': 'max-age=0', 'Expires': 'Tue, 28 Apr 2020 15:58:51 GMT', 'X-UA-Compatible': 'IE=edge', 'X-Content-Type-Options': 'nosniff', 'Content-Length': '7375', 'Keep-Alive': 'timeout=3, max=500', 'Connection': 'Keep-Alive', 'Content-Type': 'text/html; charset=utf-8'}

Links: