# 3. O introducere informală în Python

În exemplele următoare, intrările și ieșirile se deosebesc prin prezența, respectiv prin absența prompturilor (>>> și …): ca să probați un exemplu, va trebui să tastați tot ce urmează după promptul lui, atunci când vă apare promptul; liniile care nu încep cu un prompt fac parte din ieșirea interpretorului. Țineți seama de faptul că prezența promptului secundar de unul singur pe o linie dintr-un exemplu înseamnă că trebuie să introduceți o linie goală; prin aceasta se încheie o comandă de mai multe linii.

You can toggle the display of prompts and output by clicking on `>>>` in the upper-right corner of an example box. If you hide the prompts and output for an example, then you can easily copy and paste the input lines into your interpreter.

Multe din exemplele acestui manual, inclusiv cele introduse la promptul interactiv, includ comentarii. Comentariile încep în Python cu caracterul haștag, `#`, și țin până la finalul liniei fizice. Un comentariu poate apărea la început de linie, în continuarea unui spațiu gol sau a codului, dar nu în interiorul unui șir de caractere. Un caracter haștag aflat în interiorul unui șir de caractere este un simplu caracter haștag. Deoarece comentariile sunt destinate clarificării codului și nu sunt interpretate de Python, le puteți omite atunci când veți tasta exemplele.

Câteva exemple

    # this is the first comment
    spam = 1  # and this is the second comment
              # ... and now a third!
    text = "# This is not a comment because it's inside quotes."

## 3.1. Folosind Python-ul pe post de calculator

Haideți să încercăm niște comenzi simple în Python. Porniți interpretorul și așteptați să apară promptul principal, `>>>`. (N-ar trebui să dureze mult.)

### 3.1.1. Numere

Interpretorul acționează ca un simplu calculator: dumneavoastră tastați o expresie în el și el vă afișează valoarea ei. Sintaxa expresiei este una imediată: operatorii `+`, `-`, `*` și `/` se folosesc la aritmetică; parantezele (`()`) se utilizează la subexpresii. De exemplu:

    >>> 2 + 2
    4
    >>> 50 - 5*6
    20
    >>> (50 - 5*6) / 4
    5.0
    >>> 8 / 5  # division always returns a floating point number
    1.6

Numerele întregi (precum `2`, `4`, `20`) sunt de tipul `int`, cele cu parte fracționară (cum ar fi `5.0`, `1.6`) de tipul `float`. Vom reveni ulterior la tipurile numerice în tutorial.

Împărțirea (`/`) întoarce întotdeauna un număr în virgulă mobilă. Pentru a găsi partea întreagă la împărțirea cu rest, cu alte cuvinte, pentru a obține un rezultat întreg al împărțirii va trebui să folosiți operatorul `//`; pentru calculul restului, utilizați-l pe `%`:

    >>> 17 / 3  # classic division returns a float
    5.666666666666667
    >>>
    >>> 17 // 3  # floor division discards the fractional part
    5
    >>> 17 % 3  # the % operator returns the remainder of the division
    2
    >>> 5 * 3 + 2  # floored quotient * divisor + remainder
    17

În Python, puteți folosi operatorul `**` pentru a calcula puteri [1]:

    >>> 5 ** 2  # 5 squared
    25
    >>> 2 ** 7  # 2 to the power of 7
    128

Semnul egal (`=`) se folosește pentru a atribui o valoare unei variabile. După aceasta, nu se se va afișa nimic până la apariția următorului prompt interactiv:

    >>> width = 20
    >>> height = 5 * 9
    >>> width * height
    900

Dacă o variabilă nu este „definită” (nu i s-a atribuit o valoare), atunci când veți încerca să o folosiți vi se va semnala o eroare:

    >>> n  # try to access an undefined variable
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    NameError: name 'n' is not defined

Folosirea numerelor în virgulă mobilă are suport complet; operatorii cu operanzi de tipuri diferite vor converti operandul întreg la un operand în virgulă mobilă corespunzător:

    >>> 4 * 3.75 - 1
    14.0

În modul interactiv, ultima expresie afișată va fi atribuită variabilei `_`. Ceea ce înseamnă că, atunci când folosiți Python-ul drept calculator de birou, este cumva mai ușor să continuați calculele lungi, ca de exemplu:

    >>> tax = 12.5 / 100
    >>> price = 100.50
    >>> price * tax
    12.5625
    >>> price + _
    113.0625
    >>> round(_, 2)
    113.06

Această variabilă trebuie considerată ca fiind doar-de-citit de către utilizator. Nu-i atribuiți în mod explicit nicio valoare — dacă o veți face, atunci veți fi definit o variabilă locală, independentă, cu același nume, care va masca variabila predefinită în limbaj cu tot cu purtarea ei magică.

În afară de `int` și de `float`, Python-ul suportă și alte tipuri de numere, precum `Decimal` și `Fraction`. De asemeni, Python-ul are suport predefinit pentru numerele complexe și folosește sufixul `j` sau `J` pentru a desemna partea imaginară (ca în `3+5j`).

### 3.1.2. Text

Python-ul poate manipula textul (reprezentat de tipul `str`, așa-numitele „șiruri de caractere”; de la englezescul string, la singular) la fel de bine ca numerele. Acesta include caractere precum „`!`”, cuvinte cum ar fi „`iepure`”, nume ca „`Paris`”, propoziții de felul lui „`Te ajut eu.`”, șamd. „`Uraa! :)`”. Toate acestea pot fi încadrate fie de ghilimele simple (`'...'`) fie de ghilimele duble (`"..."`), cu același rezultat [2]. Exemplul care urmează folosește referințe intraductibile la scheciurile Monty Python. Astfel, apar expresiile spam eggs și Paris rabbit got your back.

    >>> 'spam eggs'  # single quotes
    'spam eggs'
    >>> "Paris rabbit got your back :)! Yay!"  # double quotes
    'Paris rabbit got your back :)! Yay!'
    >>> '1975'  # digits and numerals enclosed in quotes are also strings
    '1975'

Ca să citați ghilimelele (simple sau duble), trebuie să le „salvați” (de la englezescul escape; vom utiliza constructele: caracter escape, secvență escape, a escapa și derivate ale lor, întâlnite în literatura de specialitate) prefixându-le cu `\`. Altfel, puteți încadra textul respectiv cu celălalt tip de semne de punctuație pentru citare:

    >>> 'doesn\'t'  # use \' to escape the single quote...
    "doesn't"
    >>> "doesn't"  # ...or use double quotes instead
    "doesn't"
    >>> '"Yes," they said.'
    '"Yes," they said.'
    >>> "\"Yes,\" they said."
    '"Yes," they said.'
    >>> '"Isn\'t," they said.'
    '"Isn\'t," they said.'

În interpretorul de comenzi Python, rezultatul afișării unui șir de caractere poate să difere mult de definiția șirului de caractere. Funcția `print()` produce o afișare lizibilă a acestuia, omițând ghilimele care îl încadrează și tipărind caracterele escape, respectiv caracterele speciale:

    >>> s = 'First line.\nSecond line.'  # \n means newline
    >>> s  # without print(), special characters are included in the string
    'First line.\nSecond line.'
    >>> print(s)  # with print(), special characters are interpreted, so \n produces new line
    First line.
    Second line.

Dacă nu doriți să fie interpretate drept caractere speciale caracterele prefațate cu `\`, atunci puteți utiliza șirurile brute (de la englezescul raw) de caractere adăugând un `r` înaintea ghilimelelor simple de început:

    >>> print('C:\some\name')  # here \n means newline!
    C:\some
    ame
    >>> print(r'C:\some\name')  # note the r before the quote
    C:\some\name

Există o subtilitate vizavi de șirurile brute de caractere: un șir brut de caractere nu se poate termina cu un număr impar de caractere `\`; vedeți rubrica FAQ/IFF (întrebări formulate frecvent) pentru mai multe informații și tehnici de evitare a dificultăților.

String literals can span multiple lines. One way is using triple-quotes: `"""..."""` or `'''...'''`. End of lines are automatically included in the string, but it’s possible to prevent this by adding a `\` at the end of the line. The following example:

    print("""\
    Usage: thingy [OPTIONS]
         -h                        Display this usage message
         -H hostname               Hostname to connect to
    """)

produces the following output (note that the initial newline is not included):

    Usage: thingy [OPTIONS]
         -h                        Display this usage message
         -H hostname               Hostname to connect to

Șirurile de caractere pot fi concatenate (lipite unul de celălalt) cu operatorul `+`, respectiv repetate cu operatorul `*`:

    >>> # 3 times 'un', followed by 'ium'
    >>> 3 * 'un' + 'ium'
    'unununium'

Două sau mai multe literale șir-de-caractere (adică șiruri de caractere încadrate de semne de citare), odată ce sunt plasate unul lângă celălalt, vor fi concatenate automat:

    >>> 'Py' 'thon'
    'Python'

Această caracteristică este utilă mai ales atunci când intenționați să porționați șirurile lungi de caractere:

    >>> text = ('Put several strings within parentheses '
    ...         'to have them joined together.')
    >>> text
    'Put several strings within parentheses to have them joined together.'

Această tehnică funcționează numai cu valori literale, deci nu cu variabile și nici cu expresii:

    >>> prefix = 'Py'
    >>> prefix 'thon'  # can't concatenate a variable and a string literal
      File "<stdin>", line 1
        prefix 'thon'
               ^^^^^^
    SyntaxError: invalid syntax
    >>> ('un' * 3) 'ium'
      File "<stdin>", line 1
        ('un' * 3) 'ium'
                   ^^^^^
    SyntaxError: invalid syntax

Dacă doriți să concatenați variabile ori o variabilă cu o valoare literală, atunci folosiți `+`-ul:

    >>> prefix + 'thon'
    'Python'

Șirurile de caractere pot fi indexate (numerotate), primul caracter din șir având indicele 0. Nu există tipul caracter de sine stătător; un caracter este doar un șir de caractere cu lungimea 1:

    >>> word = 'Python'
    >>> word[0]  # character in position 0
    'P'
    >>> word[5]  # character in position 5
    'n'

Indici pot fi și numerele negative, dacă dorim să începem numărătoarea de la dreapta:

    >>> word[-1]  # last character
    'n'
    >>> word[-2]  # second-last character
    'o'
    >>> word[-6]
    'P'

Remarcați că, deoarece -0 este totuna cu 0, indicii negativi încep de la -1.

In addition to indexing, slicing is also supported. While indexing is used to obtain individual characters, slicing allows you to obtain substring:

    >>> word[0:2]  # characters from position 0 (included) to 2 (excluded)
    'Py'
    >>> word[2:5]  # characters from position 2 (included) to 5 (excluded)
    'tho'

Indicii unei tranșe au valori implicite utile; un indice de început, odată ce este omis, va fi implicit zero pe când un indice de final, omis, va lua în mod implicit ca valoare lungimea șirului de caractere în curs de tranșare.

    >>> word[:2]   # character from the beginning to position 2 (excluded)
    'Py'
    >>> word[4:]   # characters from position 4 (included) to the end
    'on'
    >>> word[-2:]  # characters from the second-last (included) to the end
    'on'

Remarcați că începutul este întotdeauna inclus, pe când finalul este întotdeauna lipsă. Această proprietate face ca `s[:i] + s[i:]` să fie egal întotdeauna cu `s`:

    >>> word[:2] + word[2:]
    'Python'
    >>> word[:4] + word[4:]
    'Python'

O metodă de a ține minte cum funcționează tranșatul este să vă imaginați indicii ca țintind între caractere, iar muchia stângă a primului caracter ca fiind numerotată cu 0. Atunci, muchia dreaptă a ultimului caracter al unui șir de caractere de n caractere va avea indexul n, ca de exemplu:

     +---+---+---+---+---+---+
     | P | y | t | h | o | n |
     +---+---+---+---+---+---+
     0   1   2   3   4   5   6
    -6  -5  -4  -3  -2  -1

Primul rând de numere dă poziția fiecăruia dintre indicii 0…6 ai șirului de caractere; cel de-al doilea rând pe cea a indicilor negativi corespunzători. Tranșa de la i la j constă din toate caracterele situate între muchiile notate cu i și respectiv cu j.

Pentru indicii nenegativi, lungimea unei tranșe este diferența indicilor, aceasta dacă amândoi sunt în limita valorilor permise. De exemplu, lungimea lui `cuvântul[1:3]` este 2.

Încercarea de a folosi un indice prea mare va conduce la o eroare:

    >>> word[42]  # the word only has 6 characters
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    IndexError: string index out of range

Cu toate acestea, indicii care depășesc plaja valorilor permise vor fi rezolvați cu eleganță atunci când îi folosim la tranșare:

    >>> word[4:42]
    'on'
    >>> word[42:]
    ''

Șirurile de caractere Python nu pot fi modificate — ele sunt imutabile. De aceea, atribuirea de valori unei poziții indexate dintr-un șir de caractere va produce o eroare:

    >>> word[0] = 'J'
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: 'str' object does not support item assignment
    >>> word[2:] = 'py'
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: 'str' object does not support item assignment

Dacă este nevoie să modificați un șir de caractere, atunci va trebui să creați un șir de caractere nou:

    >>> 'J' + word[1:]
    'Jython'
    >>> word[:2] + 'py'
    'Pypy'

Funcția predefinită `len()` returnează lungimea unui șir de caractere. Șirul de caractere supercalifragilistic… este intraductibil:

    >>> s = 'supercalifragilisticexpialidocious'
    >>> len(s)
    34

Vezi și

Tipul secvență de text – str

  Șirurile de caractere sunt exemple ale tipurilor secvență de date și permit operațiile suportate în mod obișnuit de asemenea tipuri.

Metodele șirurilor de caractere

  Șirurile de caractere suportă un număr mare de metode privind transformările uzuale și căutarea.

f-șiruri

  Valori literale șir-de-caractere care includ expresii.

Sintaxa șirurilor de format

  Informații despre formatarea șirurilor de caractere cu `str.format()`.

Formatarea șirurilor de caractere în vechiul stil printf

  Vechile operații de formatare invocate atunci când șiruri de caractere îi sunt operand stâng operatorului `%` sunt descrise în detaliu aici.

### 3.1.3. Liste

Python-ul înțelege mai multe tipuri de date compozite, folosite la punerea laolaltă de valori diverse. Cel mai versatil dintre tipuri este lista, pe care o putem scrie în formă de șir încadrat de paranteze drepte și format din valori (itemi) separate între ele prin virgule. Listele pot conține itemi de tipuri diferite, însă cel mai adesea toți itemii sunt de același tip.

    >>> squares = [1, 4, 9, 16, 25]
    >>> squares
    [1, 4, 9, 16, 25]

Aidoma șirurilor de caractere (și a tuturor tipurilor secvență predefinite), listele pot fi atât indexate cât și tranșate:

    >>> squares[0]  # indexing returns the item
    1
    >>> squares[-1]
    25
    >>> squares[-3:]  # slicing returns a new list
    [9, 16, 25]

De asemenea, listele suportă operații precum concatenarea:

    >>> squares + [36, 49, 64, 81, 100]
    [1, 4, 9, 16, 25, 36, 49, 64, 81, 100]

Spre deosebire de șirurile de caractere, care sunt imutabile, listele sunt un tip mutabil, adică este posibil să le modificăm conținutul:

    >>> cubes = [1, 8, 27, 65, 125]  # something's wrong here
    >>> 4 ** 3  # the cube of 4 is 64, not 65!
    64
    >>> cubes[3] = 64  # replace the wrong value
    >>> cubes
    [1, 8, 27, 64, 125]

You can also add new items at the end of the list, by using the `list.append()` method (we will see more about methods later):

    >>> cubes.append(216)  # add the cube of 6
    >>> cubes.append(7 ** 3)  # and the cube of 7
    >>> cubes
    [1, 8, 27, 64, 125, 216, 343]

În Python, simpla atribuire nu copiază niciodată datele. Atunci când asignați o listă unei variabile, variabila se va referi la lista de față. Indiferent ce schimbare faceți în listă prin intermediul unei variabile, schimbarea va fi vizibilă prin intermediul tuturor celorlalte variabile care se referă la prima variabilă.:

    >>> rgb = ["Red", "Green", "Blue"]
    >>> rgba = rgb
    >>> id(rgb) == id(rgba)  # they reference the same object
    True
    >>> rgba.append("Alph")
    >>> rgb
    ["Red", "Green", "Blue", "Alph"]

Toate operațiile de feliere vor returna o listă nouă conținând elementele cerute. Ceea ce înseamnă că următoarea tranșare va returna o copie superficială (de la englezescul shallow copy) a listei:

    >>> correct_rgba = rgba[:]
    >>> correct_rgba[-1] = "Alpha"
    >>> correct_rgba
    ["Red", "Green", "Blue", "Alpha"]
    >>> rgba
    ["Red", "Green", "Blue", "Alph"]

Asignarea la tranșe este, de asemenea, posibilă iar aceasta poate schimba până și mărimea listei ori șterge toate elementele ei:

    >>> letters = ['a', 'b', 'c', 'd', 'e', 'f', 'g']
    >>> letters
    ['a', 'b', 'c', 'd', 'e', 'f', 'g']
    >>> # replace some values
    >>> letters[2:5] = ['C', 'D', 'E']
    >>> letters
    ['a', 'b', 'C', 'D', 'E', 'f', 'g']
    >>> # now remove them
    >>> letters[2:5] = []
    >>> letters
    ['a', 'b', 'f', 'g']
    >>> # clear the list by replacing all the elements with an empty list
    >>> letters[:] = []
    >>> letters
    []

Funcția predefinită `len()` se aplică și la liste:

    >>> letters = ['a', 'b', 'c', 'd']
    >>> len(letters)
    4

Este posibil să imbricăm liste (de la englezescul to nest; adică să creăm liste care conțin alte liste), ca de exemplu:

    >>> a = ['a', 'b', 'c']
    >>> n = [1, 2, 3]
    >>> x = [a, n]
    >>> x
    [['a', 'b', 'c'], [1, 2, 3]]
    >>> x[0]
    ['a', 'b', 'c']
    >>> x[0][1]
    'b'

## 3.2. Primii pași în programare

Evident, putem folosi Python-ul la sarcini mult mai complicate decât la a-l aduna pe 2 cu 2. De exemplu, putem construi primii termeni ai șirului lui Fibonacci după cum urmează:

    >>> # Fibonacci series:
    ... # the sum of two elements defines the next
    ... a, b = 0, 1
    >>> while a < 10:
    ...     print(a)
    ...     a, b = b, a+b
    ...
    0
    1
    1
    2
    3
    5
    8

Acest exemplu introduce mai multe caracteristici noi.

- Prima linie conține o atribuire multiplă: variabilele `a` și `b` primesc simultan noile valori 0 și 1. Atribuirea va fi folosită din nou pe ultima linie, ceea ce ne va arăta că toate expresiile din partea dreaptă a semnului atribuirii sunt evaluate înainte să se facă orice atribuire. Aceste expresii din partea dreaptă a atribuirii se evaluează de la stânga la dreapta.

- Execuția ciclului (de la englezescul loop; vom folosi și constructele: buclă, instrucțiune iterativă, instrucțiune de ciclare, întâlnite în literatura de specialitate) `while` se repetă atâta vreme cât condiția lui (în cazul nostru: `a < 10`) rămâne adevărată. În Python, la fel ca în C, orice număr întreg nenul are valoarea logică adevărat; zero, în schimb, are valoarea logică fals. Condiția buclei poate lua chiar și valoarea unei liste ori a unui șir de caractere, în fapt, pe cea a oricărei date de tip secvență; orice obiect de lungime nenulă are valoarea logică adevărat, pe când secvențele nule au valoarea logică fals. Testul folosit în exemplu este o simplă comparație. Operatorii tipici de comparație se notează la fel ca în C: `<` (mai mic decât), `>` (mai mare ca), `==` (egal cu), `<=` (mai mic sau egal cu), `>=` (mai mare sau egal cu) și `!=` (neegal cu).

- Corpul instrucțiunii iterative are indentare: indentarea este modul în care Python-ul grupează instrucțiuni (de la englezescul statements). La promptul interactiv, trebuie să tastați fie un Tab fie un spațiu gol pentru fiecare linie cu indentare. În practică, veți prepara inputurile mai complicate destinate Python-ului cu ajutorul unui editor de text; toate editoarele de text decente posedă sisteme de indentare automată. Atunci când o instrucțiune compozită este introdusă în mod interactiv, ea trebuie urmată de o linie goală pentru a indica faptul că s-a încheiat (dat fiind că parserul nu poate ghici când intenționați să tastați utima linie de cod). Remarcați că fiecare din liniile unui asemenea bloc de cod trebuie să aibă o indentare de aceeași lungime.

- The `print()` function writes the value of the argument(s) it is given. It differs from just writing the expression you want to write (as we did earlier in the calculator examples) in the way it handles multiple arguments, floating point quantities, and strings. Strings are printed without quotes, and a space is inserted between items, so you can format things nicely, like this:

      >>> i = 256*256
      >>> print('The value of i is', i)
      The value of i is 65536

  Argumentul cuvânt-cheie end poate fi utilizat pentru a evita trecerea la o linie nouă după afișare, precum și atunci când dorim ca afișarea să se încheie cu un șir de caractere diferit de caracterul linie-nouă:

      >>> a, b = 0, 1
      >>> while a < 1000:
      ...     print(a, end=',')
      ...     a, b = b, a+b
      ...
      0,1,1,2,3,5,8,13,21,34,55,89,144,233,377,610,987,

Note de subsol

[1]

Deoarece `**` este prioritar (de la englezescul higher precedence) față de `-`, `-3**2` va fi interpretată drept `-(3**2)` și astfel rezultatul va fi `-9`. Pentru a nu se întâmpla așa ceva și a obține `9`, puteți scrie `(-3)**2`.

[2]

Spre deosebire de alte limbaje, caracterele speciale precum `\n` au aceeași semnificație indiferent dacă sunt scrise cu ghilimele simple (`'...'`) ori cu ghilimele duble (`"..."`). Singura deosebire între cele două modalități este că atunci când întrebuințăm ghilimele simple nu este nevoie să escapăm ghilimelele `"` (cu toate că trebuie escapate ghilimelele simple `\'`) și viceversa.