> For the complete documentation index, see [llms.txt](https://curropb.gitbook.io/python-notes/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://curropb.gitbook.io/python-notes/python-lesson-1.md).

# Python Lesson 1

## Lesson outline

1. `Python` programming language main features.
2. Running `Python`: Programs, `IPython`, and `Jupyter notebooks`.
3. Variable assignment and arithmetics
4. Introduction to  `Numpy`. First date…

## Running `Python`

Apart from the three methods given below you can create an independent `Python` program and launch it from a terminal. `Python` programs have the `.py` suffix and to run a program you should use the command `python filename.py`. We will go back to this at the end of the course.

The following three methods try to facilitate code development and make possible to explore results in an interactive way.

### The `Python` interpreter

You can start a `Python` interpreter in a given terminal.

```
(py3) [pts/18][curro.modesto:~]$ python
Python 3.7.4 (default, Aug  9 2019, 18:51:30) 
[GCC 7.3.0] :: Anaconda, Inc. on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> 2+2
4
>>> 
```

To exit type `CTRL-D`.

### The `IPython` console

The `IPython` project is a friendly alternative to the plain `Python` interpreter and it provides

* tab completion
* pretty-printed output
* facilitates to execute arbitrary blocks of code (%run)
* help ? and ??
* additional context if exceptions are raised
* magic commands: %run, %timeit, %%timeit

It is launched with the command

```
(py3) [pts/18][curro.modesto:~]$ jupyter qtconsole
```

Note that in some (older) environments the console should be launched as

```
(py3) [pts/18][curro.modesto:~]$hem/Python]$ ipython qtconsole
[TerminalIPythonApp] WARNING | Subcommand `ipython qtconsole` is deprecated and will be removed in future versions.
[TerminalIPythonApp] WARNING | You likely want to use `jupyter qtconsole` in the future
```

### Using `Jupyter` notebooks

This is the method we will mostly use in the course. The notebooks are launched with the command

```
(py3) [pts/18][curro.modesto:~]$ jupyter notebook
[I 18:10:08.941 NotebookApp] Serving notebooks from local directory: /home/curro/ISP/Python
[I 18:10:08.941 NotebookApp] The Jupyter Notebook is running at:
[I 18:10:08.941 NotebookApp] http://localhost:8888/?token=d3225c10006bab47630b8013dfe3961e80e8a4f751536901
[I 18:10:08.941 NotebookApp]  or http://127.0.0.1:8888/?token=d3225c10006bab47630b8013dfe3961e80e8a4f751536901
[I 18:10:08.941 NotebookApp] Use Control-C to stop this server and shut down all kernels (twice to skip confirmation).
[C 18:10:09.021 NotebookApp] 

    To access the notebook, open this file in a browser:
        file:///home/curro/.local/share/jupyter/runtime/nbserver-2413-open.html
    Or copy and paste one of these URLs:
        http://localhost:8888/?token=d3225c10006bab47630b8013dfe3961e80e8a4f751536901
     or http://127.0.0.1:8888/?token=d3225c10006bab47630b8013dfe3961e80e8a4f751536901
```

And the *landing page* will be displayed in a tab of a predefined browser. If the browser is not running it will also be launched. In the landing page click on the `New` button and select `Python 3`. A new notebook will open and you can run your first command in it.

Commands are run in cells, and one should distinguish between plain text cells, markdown cells, and command or code cells (which may have an accompanying output or not).

In markdown cells you can use this popular markup language (a superset of HTML) to add explanations and comentaries beyond the usual use of `Python` comment within code cells. Check in [jupyter markdown support](https://jupyter-notebook.readthedocs.io/en/stable/examples/Notebook/Working%20With%20Markdown%20Cells.html) to learn more about this kind of cells. You can even use LaTeX commands to include equations and formulas into these cells.

Code cells, as the rest of the cells, have two modes: *edit mode* and *command mode*. This is similar to the way the text editor `vi` works, and sometimes could be a little exasperating. It is easy to get used to it. In *command mode* the left cell edge is light blue colored and your keystrokes are translated into commands or operations within the notebook. `Jupyter` provides a list of keybord shortcuts under the menu `Help > Keyboard Shortcuts` or by pressing `H` in command mode. Some of the most useful commands are

* **A:** to insert a new cell above the current cell.
* **B:** to insert a new cell below the current cell.
* **M:** to change the current cell to Markdown.
* **Y:** to change the current cell to to code.
* **D D:** (press the key twice) to delete the current cell.
* **Shift  Tab:** to display the Docstring (documentation) for the the object you have just typed in a code cell (keep pressing this shortcut to cycle through modes of documentation).
* **Ctrl Shift -:** to split the current cell into two from where your cursor is.
* **Esc  F:** to find and replace on your code but not the outputs.
* **Esc  O:** to toggle cell output.
* **Shift Up/Down:** to select the next cell in an upwards/downwards direction.
* **Shift  M:** to merge multiple cells.

The *edit mode* is marked by a green left edge in the cell, your key typing is included as text into the cell.

You can swicth from *command* to *edit* mode (a) double clicking into the cell or (b) if the cell is highlighted, pressing `return`. To go back to *command* mode, click anywhere outside the cell or press `ESC`.

You are now ready for your first `Python` experience. Type the following statement in a cell and press `SHIFT-RETURN` to run the cell.

```
print('Hello world!')
```

When you save the notebook (the system backups them from time to time too) the information will be saved (both inputs and outputs) into an `.ipynb` file.

## Variable assignment and arithmetics

### Variable assignation

Assiging one variable value

```
mass = 64.0
print("the variable mass value is ", mass, " kg")
```

Assiging several variables simultaneously

```
first_var, second_var, forward = "hello", 243., 1
print(first_var, forward)
print(second_var)
```

You can check `Tab-completion` in the notebook. Another feature that works in the notebook is *object introspection*, using the `?` character after any instance will open a pager where a basic information about the instance is displayed.

```
forward?
```

You can check what are the variables you've created and the modules you've loaded in the notebook with the `%whos` *magic* function.

### Basic arithmetics

You can include comments in the preceding line or after your code using the hash mark (`#`).

```
# Addition
print (6+2)
# Substraction
print (6-2)
# Product and quotient
print (6*2)
print (6/2)  # Beware: difference between integer and float numbers in Python 2
# Integer quotient and modulus
print (5//2)
print (5%2)
# Raising to a power
print (6**2)
```

## Import the `Numpy` library

We start importing the `Numpy` library wich can be considered the foundational library for numerical calculations in Python.

```
import numpy as np
```

We perform some simple array operations in order to test Numpy, and its most important contribution, the `ndarray` type. It stands for *N-dimensional array object* and it is possible the most salient feature of Numpy, providing fast array-oriented arithmetics and broadcasting possibilities. Apart from this, Numpy also provides a set of mathematical functions optimized to work with such arrays, tools for file I/O, and linear algebra, fast Fourier transforms and a pseudo-random number generator (and an API for communicating with C or Fortran libraries).

We can get a first example of this structure building an array of normally distributed random data

```
nrand_array_a = np.random.randn(3,3)
print(nrand_array_a)
print(nrand_array_a*100)
print(nrand_array_a - 2*nrand_array)
```

Every Numpy array has a shape and data type that can be obtained using the `shape`, `size`, and `dtype` methods.

```
print(nrand_array_a.shape)
print(nrand_array_a.size)
print(nrand_array_a.dtype)
```

## `Numpy` first impressions

You have in Moodle a simple dataset consisting on the output of a climate model for average monthly temperatures between the years 1961 and 2096 for several cities in Cyprus. The files are of *csv* type, in the folder `TData` and can be downloaded as supplementary documentation for the course in Moodle. It will be our guinea pig in these first steps with Numpy.

### Data reading

We first read the data using the `numpy` function `loadtxt`. You can get help on it using object introspection and later we will examine with more detail file input and output.

```
np.loadtxt?
```

Read one of the provided files and store the data in a variable. You can check using tab completion if the data file path is correct.

```
metdata_orig = np.loadtxt(fname='files/TData/T_Alicante_EM.csv', delimiter=',', skiprows=1) 
```

### Data handling

You can check that the variable you've created is of `ndarry` type with `%whos` or using the `Python` function `type`

As previously, you can use the `numpy` functions `size` and `shape` to characterize the data array

```
print(np.shape(metdata_orig))
print(np.size(metdata_orig))
```

The function `dtype` has a different role, related to the building of derived types in Numpy, and it will not be addressed in this course.

In Python objects one can distinguish between *attributes* (data, objects are a named collection of attributes) and *methods* (functions). These functions provide information about the variable and they can be accessed using the syntax `variable.method`.

```
print(metdata_orig.shape)
print(metdata_orig.size)
```

Numpy arrays have some particular features that are built to optimize code speed and efficiency, saving data in contiguous memory blocks and allowing to perform complex operations on such arrays.

You can access individual array elements (negative indexes imply counting from the end of the given dimension).

```
print(metdata_orig[0,0])
print(metdata_orig[0,1])
print(metdata_orig[1,0])
print(metdata_orig[-3,3])
```

Or you can also work with full array slices or subarrays and perform operations with the arrays

```
small_a = metdata_orig[0:5,0:4]
small_b = small_a
small_c = small_a
-small_a + small_b*small_c/100
```

In this case the default initial value is zero and the default last value is the last array element. Therefore, we can extract the temperature data and remove the information about the years as follows

```
temp_data = metdata_orig[:,1:]
```

We can compute, e.g. the maximum, minimum, and average monthly temperatures for the year 1961 as

```
print('maximum monthly temperature:', np.max(temp_data[0, :]))
print('minimum monthly temperature:', np.min(temp_data[0, :]))
print('average monthly temperature:', np.mean(temp_data[0, :]))
```

As mentioned before you can use the attribute syntax, applying the `max`, `min`, and `mean` methods to the array

```
print('maximum monthly temperature:', temp_data[0, :].max())
print('minimum monthly temperature:', temp_data[0, :].min())
print('average monthly temperature:', temp_data[0, :].mean())
```

## Exercises

* **Exercise (1.1):** How would you compute minimum, maximum and average March temperatures for the given dataset?
* **Exercise (1.2):** Check the info on the numpy **mean** function and compute the average monthly temperatures and the average annual temperatures for the given dataset (Hint: axis option)
* **Exercise (1.3):** Get the *maximum* and *minimum* monthly temperatures for year 2000 and at what months did these temperatures occur.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://curropb.gitbook.io/python-notes/python-lesson-1.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
