Data limite: Entregue um pdf, via email até meia noite de 31/3
Pode ser feito individualmente ou em duplas.
Para este projeto você precisa ter o Python 3.X, numpy, matplotlib e sklearn. Provavelmente você deve também usar o jupyter como modo interativo já que ele imprime as imagens (veja abaixo) na pagina com a interação.
npy é um formato do numpy para armazenar matrizes de forma mais compacta que usando, por exemplo, um .csv
o numpy.load lê arquivos npy
X é um arquivo de 3023 linhas e 1850 colunas. Mas cada linha é na verdade uma imagem em tons de cinza de 50 por 37 pixels de pessoas famosas
X.npy esta em [http://www.ic.unicamp.br/~wainer/cursos/1s2019/X.npy
a função imshow do subpacote pyplot do matplotlib imprime uma imagem. Mas cada linha da matriz X precisa ser transformada numa matriz 50x37 para que o imshow funcione (veja o reshape do numpy). Ha também a codificação de cores da imagem; como a imagem é em tons de cinza a codificação é a cm.gray
A função é svd, do subpacote linalg do numpy faz a fatoração svd.
Lembre-se que nos vimos várias formulações para a fatoração SVD
\(A = U D V^{-1}\)
onde A é m x n.
Na primeira formulação (do wikipedia por exemplo), que nós chamamos de full matix
U é m x m
D é m x n
e \(V^{-1}\) é n x n
Esta fatoração é obtida pelo svd quando o parâmetro full_matrices é True
A segunda formulação que acho que chamamos de compacta é
U é m x n
D é n x n
e \(V^{-1}\) é n x n
que é obtida quando full_matrizes é False.
Gere as 2 fatorações svd e mostre que as matrizes são dos tamanhos corretos.
Verifique o maior valor em modulo da diferença
\(X - (U D V^{-1})\)
usando a 2a formulação. O maior valor em modulo é o maior erro da fatoração em relação a algum dado original. Compare esse valor do maior erro com o valor médio dos dados em X. Verifique que o erro é bem baixo.
Note que o svd do numpy não retorna D como uma matriz (n x n) mas sim como um vetor com os elementos da matriz diagonal.
Vamos usar a redução para 100 dimensões.
O objetivo da redução da dimensionalidade da matriz X (3023 x 1850) é obter uma matriz com menos colunas \(k < 1850\) que representa mais ou menos a mesma informação que X, mas com menos espaço de memória.
Neste exercício, vamos usar k=100, ou seja queremos projetar cada imagem (que esta num espaço de 1850 dimensões) no melhor subespaço de 100 dimensões (quase 5% do número de dimensões originais) que representa ainda dos dados. Ou de outra forma, encontrar o subespaço de 150 dimensões cujo erro (quadrado) entre o dado original e sua projeção nesse subespaço seja a menos possível.
A matriz reduzida de X será uma matriz de 3023 linhas (o mesmo numero de dados/imagens) mas de 100 colunas.
A formulação do SVD para redução de dimensionalidade é
\(X \approx U_k D_k V_{k}^{-1}\)
onde
\(U_k\) é a matriz U com apenas as primeiras k colunas \(D_k\) é a matriz diagonal D com apenas as primeiras k linhas e colunas
Ou seja, X é aproximado pelo produto \(U_k D_k V_k^{-1}\)
A matriz \(U_k D_k\) é a matriz reduzida - cada ponto de dado original (3023 deles), que antes tinha 1850 dimensões, agora tem 100 dimensões!
A matriz reconstruída é uma matriz no espaço original (de 1850 dimensões) onde em vez da posição original de cada ponto, a linha representa a posição (no espaço de 1850 dimensões) da projeção do ponto no subespaço de 100 dimensões.
A matriz reconstruída deve ter 1850 dimensões mas em vez da imagem original. temos a imagem quando projetada no subespaço de 100 dimensões da redução.
A formula para a matriz reconstruída \(X_r\) é:
\(X_r = U_k D_k V_k^{-1}\)
Gere as matrizes reduzidas e reconstruídas com redução para 100 dimensões
Compare com a imagem original impressa acima
Para computar a matriz reduzida (que não vamos usar para nada) e a matriz reconstruida (a ser usada nessa seção) use ambos as funções svd do numpy que usamos acima (que gera apenas a matrizes full ou compactas) e a função TuncatedSVD do scikit-learn que computa apenas a formulação truncada (dado o k).
Nota: eu mencionei a função svds em classe, mas essa função que computa o SVD truncado, mas eu nao notei que ela computa o SVD truncado apenas para matrizes esparsas!!!
Use tanto o svd do Numpy removendo as colunas e linhas na mao e a função TruncatedSVD para computar a matriz reconstruida, em particular a imagem da primeira pessoa!