NumPy e suas arrays

NumPy abreviação para Numerical Python é uma Lib fundamental para quem planeja lidar com computação numérica de alta performance em Python. Ele é a base de muitos outros Módulos e frameworks de alto nível como Pandas, Matplotlib, Scikit-learn, Opencv dentre outros não menos importantes.

É primordial avisar que esse post é apenas uma demonstração básica de como funciona as arrays do NumPy é justamente para pessoas que nunca tiveram contato com essa Lib. Agora se você já teve contato com a mesma antes, provavelmente não lhe acrescentará muita coisa. Mas fique de olho que já tenho alguns posts interessantes sobre o assunto na fila.

NumPy foi pensado para lidar com  cálculo vetorial. Isso quer dizer que possui uma série de funcionalidades para lidar com vetores,matrizes e tensores, isso facilita realizar programação funcional e aplicações de funções a todos os elementos de um vetor ou nás diferentes dimensões de um tensor ou matriz.

Sem contar com suas ferramentas para lidar com variáveis aleatórias, Álgebra linear e as integrações com as linguagens C, C++ e Fortran. Em outras palavras, é um pré-requisito para quem planeja lidar com Machine Learning, Análise de dados, Engenharia de dados e computação científica em geral.

Falarei no post de hoje de algumas funções básicas usadas para criar arrays ou np.ndarrays como é definido o nome do objeto no Python.

As arrays do NumPy

As  Arrays formam o coração do NumPy. Tudo nessa Lib é destinado simplesmente para lidar com arrays, tanto de uma única dimensão como N dimensionais.

Vamos a um exemplo de como criar uma array em NumPy.

#Vamos importar a Lib da forma mais convencional.
In [2]: import numpy as np

In [3]:data = [1,2,3,4,5,6]

In [4]: arr1 = np.array(data)

In [5]: arr1
Out[5]: array([1, 2, 3, 4, 5])

É muito comum criarmos as arrays a partir de listas, mas podemos criar a partir de tuplas ou sets também. E ate mesmo gerá-las com algumas funções específicas.

Elas lembram o objeto list do Python mas são outra coisa. Possui centenas de métodos e atributos para lidar com vetores e matrizes de dados.

Podemos usar outros métodos para criar arrays específicos de acordo com a necessidade.

#.zero() é um método que cria uma array de zeros com o tamanho desejado.
In [19]: np.zeros(10)
Out[19]: array([ 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.])

#Podemos criar uma array de duas dimensões também!
In [20]: np.zeros((3, 6))
Out[20]:
array([[ 0., 0., 0., 0., 0., 0.],
       [ 0., 0., 0., 0., 0., 0.],
       [ 0., 0., 0., 0., 0., 0.]])

#Podemos criar arrays vazias, útil caso queira criar novos objetos ou DataFrames
#Não é criado apenas arrays vazias elas vem com valores aleatórios as vezes
In [21]: np.empty((5,2))
Out [21]:
array([[ 0.,0.],
       [ 0.,0.],
       [ 0.,0.],
       [ 0.,0.],
       [ 0.,0.]])

#.arange é um método muito interessante assim com o range do Python ela cria uma array de 0 a n-1
#nas verções mais atuais do Python o método range cria um generator e não mais uma lista.
In [22]: np.arange(15)
Out[22]: array([ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14])

Um método interessante é .asarray() quando usamos ele em uma lista comum ele cria uma array porém quando aplicado a uma array ele armazena o mesmo objeto dentro da variável ao invés de criar uma cópia.

In [23]: data = [[1,2],[5,6],[7,2]]

#Crio uma array comum
In [24]: arr1 = np.array(data)

#Faço outra array comum a partir da array antiga
In [25]: arr2 = np.array(arr1)

#Comparo os dois objetos e retorna False. são instâncias diferentes.
In [26]: arr1 is arr2
Out [26]: False

#Agora crio um novo objeto com .asarray()
In [27]: copy_arr1 = np.asarray(arr1)

#Comparo os dois objetos e retorna True são o mesmo objeto.
#As alterações que forem feitas em um afetam o outro.
In [28]: copy_arr1 is arr1
Out [28]: True

#Gostaria de lembrar que o método .asarray tem o mesmo efeito do método .copy
#Quando aplicado a uma array do Numpy.
#O método .ones() assim como .zeros() cria uma array porem de 1 e 0 respectivamente.
In [29]: np.ones(5)
Out [29]: array([ 1., 1., 1., 1., 1.])

#O método .ones_like() pega outra array qualquer e a transforma em uma array de 1.
#Util para reaproveitar memoria
In [30]: arr1 = np.array([[1,2],[5,6],[7,2]])

In [31]: np.ones_like(arr1)
Out[31]:
array([[1, 1],
       [1, 1],
       [1, 1]])

Temos também os métodos .zeros_like() e .empty_like que fazem a mesma coisa que .ones_like() porem com zeros e array vazia respectivamente.

Outro método interessante para quem lida com matrizes é o .eye() que cria uma matriz NxN identidade. Dê uma olhada:

#No caso criei um array 3 por 3 com 1 na diagonal.
# Em algebra linear isso é a famosa matriz identidade
In [32]: np.eye(3)
Out[63]:
array([[ 1., 0., 0.],
       [ 0., 1., 0.],
       [ 0., 0., 1.]])

Esse foi o post de hoje dos meus queridos 7 leitores.  Se você achou básico, a proposta era justamente essa: apenas uma demonstração das arrays do NumPy para despertar seu interesse nessa lib.

Qualquer dúvida, crítica ou sugestão é só deixar nos comentários que respondo imediatamente. Caso queira uma demonstração do NumPy mais interessante, fiz um post sobre Decision Trees em que utilizei ele.

Segue o link:  Decision trees com sklearn parte 1

Se você se interessou e planeja aprender NumPy recomendo fortemente esses dois livros Python Para Análise de Dados: Tratamento de Dados com Pandas, NumPy e IPython e Scipy lecture notes.

Bons estudos.

Dicas de estudos para aprender Machine Learning

Acredito que a maior duvida de quem estar interessado em aprender e aplicar Machine learning é justamente por onde começar. Apesar de me considerar um iniciante na arte de ensinar máquinas passei e ainda passo bastante tempo pesquisando quais os tópicos necessários e em qual ordem estudá-los.

Acabei me deparando com uma grande quantidade de opiniões diferentes sobre o que deve ser aprendido e o que deve ser evitado. Mas mesmo assim criei um organograma com alguns tópicos para estudar junto com algumas descrições.

Matemática teórica e aplicada

Tudo bem que não é necessário ser um matemático para aprender Machine learning, mas é necessário aprender alguns tópicos básicos.

Álgebra linear: Muitos dizem que Álgebra linear é a matemática do futuro, eu pessoalmente acho que é a matemática do agora.

Aqui aprendemos a lidar com matrizes, espaços vetoriais, transformadas, vetores, autovetores, diagonalizar matrizes dentre várias outras coisas. Álgebra linear(e não só.) é a base de muitos tópicos relevantes em Estatística e Probabilidade, Otimização e calculo com múltiplas variáveis em geral. Se acostumar com as notações dessa disciplina é essencial para compreender artigos ou livros de Machine learning com uma pegada mais teórica.

É muito comum representar conjuntos de testes ou treino como matrizes ou suas linhas ou colunas como vetores, isso nos ajuda a ter uma visão mais abstrata dos algoritmos e facilita a interpretação e aplicação dos mesmos.

para quem gosta de ler livros eu com certeza não posso deixar de indicar o livro Álgebra Linear com aplicações um excelente livro que não pode faltar na sua prateleira.

Cálculo diferencial e integral: Acredito que não precisamos saber tudo sobre cálculo mas algumas técnicas de derivação e integração são indispensáveis para não passar raiva na hora de aprender um algoritmo novo e principalmente na hora de entender um algoritmo para otimização de redes neurais chamado gradiente descendente estocástico 

acredito que para esse fim não exista livro melhor do que o bom e velho James Stewart.

 

Estatística e probabilidade: Acredito que não seja necessário saber tudo sobre isso, mas acho que onde se deve gastar mais tempo estudando. Aqui aprendemos a lidar e representar incertezas derivadas do desenvolvimento e aplicação de um modelo.

Tópicos como média, moda, variância, desvio padrão, algumas medidas de dispersão, variáveis aleatórias, teorema de Bayes são alguns dos pré requisitos para começar a entrar de vez nessa área.

Uma coisa interessante nesse tópico é aprender a identificar o tipo de distribuição probabilística que um conjunto de dados possui, isso afeta na hora de escolher o modelo. Por mais que a tendência seja transformar tudo isso em uma caixa preta saber lidar com Estatística e Probabilidade pode ser um diferencial e tanto no futuro.

Um livro que achei muito interessante é o Estatística Aplicada e Probabilidade para Engenheiros. Tratasse de um livro introdutório e pragmático com um série de exemplos e aplicações muito interessantes.

Otimização: Acho que de todos os tópicos esse é o que menos sei, alias eu o estudo sobre demanda, mas percebi com minhas pesquisas que a maioria dos problemas de aplicações em  Machine Learning são problemas de otimização.

Geralmente sempre temos que achar o valor mínimo para uma determinada constante de modo que satisfaça alguma condição.

Entender funções convexas, o que é otimizável ou não. porque usar uma algoritmo e não outro pode lhe render um diferencial estratégico e tanto na hora de aplicar os algoritmos.

Não irei indicar um livro hoje pois ainda estou lendo um,

Muita paciência: Para você que vem da programação já deve estar acostumado a aprender sobre demanda, encontrar materiais práticos e tal.

Aprender matemática não é bem assim, a curva de aprendizado é bem menos inclinada no início depois ate que dar uma inclinada, mas tende a reduzir sua inclinação com um tempo. Isso acontece pois os conceitos começam a se tornar cada vez mais complexos o que demanda muito tempo para serem totalmente assimilados.

O que aconselho é criar o habito de estudar matemática diariamente, e vá estudando as outras coisas mais praticas junto.

O mais legal da matemática é que quando vamos ficando realmente bons conseguimos enxergar padrões em estruturas que antes não faziam sentido. Ao contrário do que muitos pensam quanto mais matemática sabemos menos cálculos necessitamos para lidar com os assuntos.

Claro que existem outros tópicos como Analise Real, Teoria da informação, Matemática discreta e Teoria dos grafos.  Mas não acredito que seja necessário para quem quer somente  aplicar ML  na prática.

Caso você se interessou por matemática e queira dar uma aprofundada no assunto eu aconselho antes de tudo o curso: Introduction to Mathematical Thinking

As linguagens de programação.

Acho que esses são os tópicos mais estudados sobre Machine Learning pois por serem mais práticos são bem mais fáceis de aprender do que a Matemática teórica.

Não da para começar a lidar com Machine Learning sem antes ter um bom domínio de uma linguagem de programação. Alias se você não sabe programar não perca tempo e escolha sua linguagem só depois de estar no mínimo mediano volte a estudar ML.

Listo abaixo algumas das linguagens de programação mais recomendadas segundo minha experiência e alguns artigos que li.

Python: Essa é a minha linguagem oficial. Com certeza vale a pena aprender, é uma linguagem fácil de aprender tem uma comunidade forte e muitos Modulos,libs e Frameworcks voltados para Machine Learnig e Data science como um todo.

A única coisa que acho um pouco chato em Python é para visualizar os dados a lib Matplotlib não é muito intuitiva para aprender, provavelmente você irá passar raiva na hora de visualizar os dados, eu pessoalmente fico frustrado com algumas funcionalidades do Matplotlib e também não é uma linguagem robusta como Java ou C++ por isso na hora de colocar os projetos na prática seja melhor usar uma linguagem mais performática.

Mas mesmo assim Python com certeza é uma das estrelas do Data science e a cada dia ganha mais interface com ferramentas feitas em outras linguagens.

um curso muito interessante para aprender python aplicado a área é Ciência de dados

R: Eu não diria que R é exatamente uma linguagem, é mais um conjunto de ferramentas para lidar com vetores, o que faz dela uma excelente ferramenta para lidar com Estatística, eu ainda me considero um Noob nessa linguagem, mas mesmo assim já consigo tirar vantagem das Packages para visualização de dados que ca entre nos são bem mais intuitivas do que a do Matplotlib.

A desvantagem é que como é um linguagem de proposito especifico não serve para aplicar o algoritmo na prática, a não ser que seja para fazer relatórios claro. Mas o interessante é que é muito mais fácil fazer os protótipos em R e depois é só implementar com uma linguagem mais robusta.

C++  e Java: Eu pessoalmente entendo muito pouco dessas linguagens, mas são linguagens mais robustas e servem para fazer o algoritmo rodar pra valer.

Apesar de saber poucos sobre elas sei da relevância de cada uma acredito que dominar uma dessas linguagens pode nos tornar melhores programadores.

Se o intuito for ser um Engenheiro de Machine Learning por exemplo, fazer as coisas rodarem na prática é pre requisito, e certamente tera contato com aplicativos construídos nessas linguagens.

SQL: Todo mundo aconselha aprender SQL, o motivo provavelmente é que a maioria dos dados estruturados do mundo estejam armazenados em bancos de dados que usam essa linguagem.

Meu conselho é: Aprende essa parada, infelizmente não tenho tanto conhecimento em SQL para dar mais algum motivo plausível mas já nas primeiras aplicações de Machine learning vi uma necessidade de se comunicar com algum banco de dados.

Conclusão.

Acredito que depois que você tiver pelo menos 50% dos conhecimentos acima principalmente os de programação e Álgebra linear já estará apto a brincar com alguns algoritmos.

Claro que ficar apenas na linguagem pura não é uma boa ideia pois isso torna inviável sua aplicação e também é bem menos produtivo.

Eu pessoalmente aconselho a aprender ferramentas como PandasNumpyMatplotlib, SKlearn, Opencv, Tensor flow, Theano, NLTK , Caffe, dentre varias outras que existem atualmente. Falarei mais sobre algumas delas em futuros posts.

Valeu galera esse foi o post de hoje espero que tenha sido útil e ate o próximo.

Bias e Variância,Underfitting e overfitting

Para você que já vem estudando Machine Learning já deve ter se deparado com a seguinte situação. Seu algoritmo depois de treinado fazer maravilhas no conjunto de treino,  mas quando aplicado ao conjunto de teste,  ter um erro terrível. Ou o contrário disso! ter um desempenho ruim no conjunto de treino e acertar de maneira ate decente no conjunto de teste, caso ainda não tenha passado por isso é bom saber o que significa pois a probabilidade de acontecer com você no futuro é bem alta.

Primeiramente vamos definir cada um dos três termos apresentados no título.  Depois analisar o comportamento de dois algoritmos simples e identificar o que é o Bias de um algoritmo e quando estamos diante de um caso de Underfitting ou overfitting.

Bias

O Bias(que pode ser traduzido como o viés) não é algo muito fácil de definir, para se ter uma ideia existem ate discussões filosóficas em torno do assunto, mas quero demonstrar de maneira intuitiva do que se trata.

O exemplo abaixo foi inspirado no do livro A curse in Machine Learning.

De uma olhada na imagem abaixo:

figura - 1

Agora use o que você aprendeu para classificar as figuras a seguir.

figura - 2

Alguns de vocês, eu arrisco dizer a grande maioria, ira classificar como ABABB enquanto outros irão classificar como ABBBA, pode parecer um pouco estranho mas isso acontece devido ao Bias indutivo(Inductive bias.) que cada um teve para tomar sua decisão.  e com isso  aprender com a primeira imagem.

Pois nesse caso temos no mínimo dois jeitos de aprender.  O primeiro seria a classificação entre animais voadores e terrestres enquanto o segundo seria entre animais mamíferos e aves.

No exemplo acima caso a tarefa aprendida fosse separar entre mamíferos e aves o atributo mais relevante iria ser as penas com certeza.

Caso fosse separado entre voadores e terrestres o atributo mais importante iria ser as asas pois assim não deixaria o morcego passar direto.

Quando pensamos em algoritmos já é um pouco mais complicado definir um Bias pois cada algoritmo tende a ter comportamentos bem diferentes e por consequência valorizar diferentes características.

Mas por hora podemos definir Bias como o objetivo a ser aprendido aquilo que nos ira levar a decisão correta.

Em contraste com o Bias temos a variância, quando um algoritmo tem uma variância muito alta ele se torna sujeito a levar em conta ruídos ou dados específicos demais.

Começa a levar em conta características que não são importantes para a tarefa como a cor das penas por exemplo.

O ideal é ter um algoritmo equilibrado que não tenha um Bias muito elevado pois isso pode fazer com que ele não tenha a complexidade necessária para classificar as instâncias corretamente Mas que também não tenha uma variância muito alta para não considerar ruídos e dados aleatórios.

Modelos com alto Bias tendem a fazer maiores conclusões sobre um conjunto de dados a partir de poucos atributos, as funções que mapeiam o conjunto são menos complexas tendem a ter uma maior taxa de erro no conjunto de teste.

Já modelos com alta variância tendem a tomar decisão utilizando uma grande quantidade de atributos o que os tornam vulneráveis a ruídos.

Underfitting e overfitting

Como vimos acima fica claro que nosso algoritmo não pode generalizar demais porém não pode ser especifico demais o que precisamos é de um algoritmo equilibrado.

Existe dois jargões usados em ML que resume bem cada situação.  Vamos falar delas agora.

Underfitting: Quando você treina seu modelo e testa ele no próprio conjunto de treino e percebe que ele ainda tem uma taxa de erro considerável e então testa ele no conjunto de teste e percebe que a taxa de erro é semelhante mas ainda alta.

Isso quer dizer que estamos diante de um caso de Underfitting o modelo tem um alto Bias e ainda podemos melhorar sua classificação, para isso deveremos mexer em alguns parâmetros do algoritmo.

Claro que em nem todos os casos ira ocorrer dessa forma depende da natureza do algoritmo utilizado para treina-lo.

Overfitting: Agora você treinou seu modelo e depois disso resolveu aplicá-lo em seu conjunto de treino e fica feliz quando percebe que ele teve uma taxa de erro de 00,35% por exemplo. Mas quando aplica no conjunto de teste percebe que ele tem um desempenho horrível.

Estamos diante de um caso de Overfitng, o Algoritmo tem baixo Bias não consegue generalizar muito bem, Isso acontece pois tem mais complexidade do que o necessário, considera atributos que não deveria. E muito desses são provavelmente ruídos.

Nesse caso devemos deixar o algoritmo mais livre para conseguir generalizar melhor.

É importante lembrar que ter uma alta taxa de acerto no conjunto de treino não diz necessariamente que o modelo esta em overfitting.

Vamos a dois casos práticos.

Para quem já vem estudando Machine Learning a um tempo já deve ter passado por esses dois algoritmos o KNN e Decision tree.

K-nearest neighbors: Esse algoritmo se utiliza de propriedades geométricas para tomar suas decisões ele usa o conjunto de treino toda vez que precisa classificar uma nova instância. Para isso ele calcula a distância do vetor em relação a todos os outros vetores, depois ele classifica aquele vetor como sendo da classe dos K vetores mais próximos

figura - 3

Como você pode ver na imagem acima ele mede a distância entre o vetor em relação aos seus vizinhos mais próximos (Nesse caso 3.) e logo em seguida a classifica como sendo da mesma classe dos dois vizinhos mais próximos, no caso um ponto verde.

Olhando dessa forma podemos perceber que o parâmetro que ira alterar o Bias de nosso algoritmo é o próprio K caso coloquemos ele para calcular a distância entre os 99 vizinhos mais próximos pode haver uma alteração na classificação.

Observe o gráfico abaixo:

figura - 4

Devido a natureza do KNN quando aumentamos o número de vizinhos a taxa de erro é aumentada tanto no conjunto de treino quanto de teste mesmo assim a taxa aumenta no conjunto de teste há uma velocidade menor.

Isso acontece pois ele usa o próprio conjunto de treino como parte do algoritmo, mas fica claro que quanto mais vizinhos colocamos mais propenso a overfitting ele se torna. Porem quando temos menos vizinhos a taxa de erro nos dois conjuntos fica bem perto de zero isso acontece pois usei um conjunto de dados pequeno.

Caso queira saber mais sobre o algoritmo tem  mais sobre ele aqui.

Decision tree: É um algoritmo determinístico ele procura no conjunto de dados uma maneira de separar as instâncias de acordo com o ganho de informação de seus atributos, isso faz com que o modelo tenha a topologia de uma árvore.

dt

Nos chamamos de profundidade(depth) da árvore a quantidade de Nodes( as bolinhas) com ramos para outros Nodes da árvore,  quando não tem ramo é chamado folha,  que é por onde a instância será classificada.  Fica claro que um dos parâmetros que ira influenciar no Bias é sua profundidade e a quantidade de atributos que pode ser usada para medir a pureza do conjunto.

Medir o desempenho de uma DT não é tão simples quanto o do KNN mas vale a pena fazer algumas observações simplistas para entender o comportamento desse modelo.

Apliquei uma DT no conjunto de dados Titanic usei apenas três atributos Sexo, Idade e Classe da cabine.

Primeiro medi o desempenho de uma árvore usando apenas um atributo em diferentes profundidades.

Observe o gráfico abaixo.

grafico-1

Repare na linha azul ela começa bem alta depois desse ate um limite e volta a aumentar. isso acontece pois como só foi usado um atributo para treinar a árvore ela tem pouca informação para achar algum padrão quando a profundidade é pequena. Isso esta em um estado de Underfitting significa alto Bias.

 

imagem_1

 

Em contraste, quando a profundidade vai aumentando ela tende aumentar a variância e começa a generalizar meno,  isso é um estado de Overfitting.

grafico-2

Com uma atributo a mais a a taxa de erro no conjunto de treino começa a baixar bem mais cedo. Ela tende a entrar em estado de Overfiting mais rápido. Isso acontece pois como temos uma quantidade maior de atributos não é necessária uma árvore muito profunda para captar os padrões mais relevantes.

grafico-3

Agora com três atributos a taxa de erro no conjunto de treino fica baixa ainda mais rápido por mais que a taxa de erro tenda a baixar em uma profundidade maior é preciso ficar atento a maneira de como o conjunto estar organizado alguns fatores como a ordem de entrada dos dados tem bastante influência.

Então é isso pessoas. Este foi o Post de hoje espero que tenha contribuído para seu aprendizado dessa área fascinante que é Machine Learning.

Gostou do que viu? E quer começar nessa área fascinante. Eu recomendo fortemente o curso Curso Ciência de Dados . Depois de fazer esse curso você será capaz de aplicar os conceitos básicos da área e de quebra aprender o ferramental disponível em Python para essa área. Vale a pena dar uma conferida.