Pular para o conteúdo

    Capítulo 5, Básico

    Criando arrays

    Todo array nasce de duas formas: a partir de dados que você já tem, ou gerado na hora, com a forma que você pedir. O NumPy tem uma função para quase toda situação.

    Código deste capítulo: básico/cap05_criando_arrays.py

    A partir dos seus dados

    O np.array converte listas (e listas de listas) em um array. Listas aninhadas viram dimensões:

    básico/cap05_criando_arrays.pylinhas 10 a 13
    import numpy as np
    
    print(np.array([1, 2, 3]))
    print(np.array([[1, 2], [3, 4]]))
    
    Saída
    [1 2 3]
    [[1 2]
     [3 4]]
    

    Todas as linhas precisam ter o mesmo tamanho. Um array é uma grade retangular, e o NumPy recusa uma estrutura "irregular" em vez de adivinhar o que você quis dizer:

    básico/cap05_criando_arrays.pylinhas 15 a 18
    try:
        np.array([[1, 2], [3]])
    except ValueError as erro:
        print("erro de forma irregular:", "inhomogeneous" in str(erro))
    
    Saída
    erro de forma irregular: True
    

    Arrays de preenchimento: você dá a forma

    Quando você ainda não tem os valores, mas sabe a forma, os arrays de preenchimento reservam o espaço. A forma é uma tupla, e é aí que mora o erro mais comum:

    básico/cap05_criando_arrays.pylinhas 23 a 25
    print(np.zeros((2, 3)))
    print(np.ones((2, 3), dtype=int))
    print(np.full((2, 3), 7))
    
    Saída
    [[0. 0. 0.]
     [0. 0. 0.]]
    [[1 1 1]
     [1 1 1]]
    [[7 7 7]
     [7 7 7]]
    
    básico/cap05_criando_arrays.pylinhas 27 a 30
    try:
        np.zeros(2, 3)
    except TypeError as erro:
        print(erro)
    
    Saída
    Cannot interpret '3' as a data type
    

    Escrevendo np.zeros(2, 3), o NumPy entende o 3 como o tipo de dado (o segundo parâmetro), e por isso a mensagem fala em "data type". A forma é um único argumento: np.zeros((2, 3)), com parênteses duplos.

    O np.empty também reserva a forma, mas não inicializa a memória: o conteúdo é o que já estava lá, e não zero. Ele é um pouco mais rápido que o zeros, e só serve quando você vai sobrescrever todos os valores logo em seguida. Eu raramente o uso, porque o ganho é pequeno e o risco de ler lixo é real.

    Matrizes especiais

    básico/cap05_criando_arrays.pylinhas 35 a 36
    print(np.eye(3))
    print(np.diag([1, 2, 3]))
    
    Saída
    [[1. 0. 0.]
     [0. 1. 0.]
     [0. 0. 1.]]
    [[1 0 0]
     [0 2 0]
     [0 0 3]]
    

    O np.eye(3) é a matriz identidade (uns na diagonal). O np.diag monta uma matriz diagonal a partir de uma lista, e, se receber uma matriz, faz o caminho inverso e extrai a diagonal.

    Sequências

    básico/cap05_criando_arrays.pylinhas 41 a 43
    print(np.arange(0, 10, 2))
    print(np.linspace(0, 1, 5))
    print(np.logspace(0, 2, 3))
    
    Saída
    [0 2 4 6 8]
    [0.   0.25 0.5  0.75 1.  ]
    [  1.  10. 100.]
    

    O arange funciona como o range do Python: início, fim (excluído) e passo. O linspace recebe o número de pontos e inclui os dois extremos. O logspace espaça os pontos em escala logarítmica, de 10⁰ a 10², três pontos.

    arange com passo decimal

    Com passos decimais, o arange acumula erro de ponto flutuante e pode surpreender no tamanho do resultado. Quando você sabe quantos pontos quer, o linspace é mais previsível:

    básico/cap05_criando_arrays.pylinha 45
    print(len(np.arange(0, 1, 0.1)), len(np.linspace(0, 1, 11)))
    
    Saída
    10 11
    

    O arange produz 10 pontos e exclui o 1. O linspace(0, 1, 11) produz 11 e inclui os dois extremos. Em dúvida, use linspace.

    Arrays com a forma de outro

    As funções *_like criam um array com a mesma forma (e o mesmo tipo, a menos que você diga o contrário) de um array existente:

    básico/cap05_criando_arrays.pylinhas 50 a 52
    base = np.array([[1, 2, 3], [4, 5, 6]])
    print(np.zeros_like(base))
    print(np.ones_like(base, dtype=float).shape)
    
    Saída
    [[0 0 0]
     [0 0 0]]
    (2, 3)
    

    O capítulo 16 apresenta os arrays aleatórios, que também são uma forma de criação.

    Exercício 1

    Múltiplos e matrizes constantes

    Escreva multiplos_de(passo, limite) que devolva os múltiplos de passo de 0 até limite (inclusive), e matriz_constante(linhas, colunas, valor).