Dimensionality Reduction

Introduction

Dimensionality Reduction is one of the method in a machine learning. Dimensionality reduction can be used for image compression. Image compression is a method that reduces an image’s bytes size while maintaining as much of the image’s quality as possible.

There are three ways of reducing dimensionality. In my case I will use PCA( Principal Component Analysis).

Firstly we need following packages.

library(jpeg)
library(factoextra)
## Loading required package: ggplot2
## Welcome! Want to learn more? See two factoextra-related books at https://goo.gl/ve3WBa
library(gridExtra)
library(ggplot2)
library(magick)
## Linking to ImageMagick 6.9.12.3
## Enabled features: cairo, freetype, fftw, ghostscript, heic, lcms, pango, raw, rsvg, webp
## Disabled features: fontconfig, x11
library(png)
#library(Metrics)
library(knitr)
library(imgpalr)
library(abind)

Now we can run the image.

getwd()
## [1] "C:/Users/Maryam/Downloads"
italy <- readJPEG("italy.jpg")

plot(1, type="n")
rasterImage(italy, 0.5, 0.5, 1.5, 1.5)

From the image you can see different light colors. Lets change all colors to one color.

italy.sum<-italy[,,1]+italy[,,2]+italy[,,3]
italy.bw<-italy.sum/max(italy.sum)

plot(1, type="n")
rasterImage(italy.bw, 0.5, 0.5, 1.5, 1.5)

PCA

I will use PCA now for dimensian reduction. As we know that it has three tones ; the R, G, and B tones.

So we will implement them to our image.

r<-italy[,,1] # individual matrix of R color component
g<-italy[,,2] # individual matrix of G color component
b<-italy[,,3] # individual matrix of B color component


r.pca<-prcomp(r, center=FALSE, scale.=FALSE) # PCA for r
g.pca<-prcomp(g, center=FALSE, scale.=FALSE) # PCA for g
b.pca<-prcomp(b, center=FALSE, scale.=FALSE) # PCA for b 

We can combine three PCAs in one place.

rgb.pca<-list(r.pca, g.pca, b.pca)

Now look at PCA influence on our case.

f1<-fviz_eig(r.pca, main="black", barfill="black", ncp=5, addlabels=TRUE)
f2<-fviz_eig(g.pca, main="yellow", barfill="yellow", ncp=5, addlabels=TRUE)
f3<-fviz_eig(b.pca, main="red", barfill="red", ncp=5, addlabels=TRUE)
grid.arrange(f1, f2, f3, ncol=3)

From the graph we can see the realtionship between Percentages of explained variables and Dimensions. The score of variances are near to 80% and more than 80%.

Make an image clear from bulur version.

vec<-seq.int(3, round(nrow(italy)), length.out=9)
for(i in vec){
  italy.pca<-sapply(rgb.pca, function(j) {
    new.RGB<-j$x[,1:i] %*% t(j$rotation[,1:i])}, simplify="array")
  assign(paste("italy_", round(i,0), sep=""), italy.pca)
  writeJPEG(italy.pca, paste("italy_", round(i,0), "_princ_comp.jpg", sep=""))
}


par(mfrow=c(3,3)) 
par(mar=c(1,1,1,1))

plot(image_read(get(paste("italy_", round(vec[1],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[2],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[3],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[4],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[5],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[6],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[7],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[8],0), sep=""))))
plot(image_read(get(paste("italy_", round(vec[9],0), sep=""))))

The last one is the clearest image.

Creating palette

We can create a palette from our image.

colors1<-image_pal("italy.jpg", n=8, type="div", saturation=c(0.75, 1), brightness=c(0.75, 1), plot=TRUE)

colors2<-image_pal("italy.jpg", n=11, type="seq", k=2, saturation=c(0.5, 1), brightness=c(0.25, 1), seq_by="hsv", plot=TRUE)

From the results we can see the most used colors are green and purple.

Principal Component Comperssion- PCC

When we want to reduce the size of our pic we can use this method.

We can use the MSE for comparing.

library(Metrics)

sizes<-matrix(0, nrow=9, ncol=4)
colnames(sizes)<-c("Number of PC", "Photo size", "Compression ratio", "MSE-Mean Squared Error")
sizes[,1]<-round(vec,0)
for(i in 1:9) {
  path<-paste("italy_", round(vec[i],0), "_princ_comp.jpg", sep="")
  sizes[i,2]<-file.info(path)$size 
  italy_mse<-readJPEG(path)
  sizes[i,4]<-mse(italy, italy_mse) # from Metrics::
}
sizes[,3]<-round(as.numeric(sizes[,2])/as.numeric(sizes[9,2]),3)
sizes
##       Number of PC Photo size Compression ratio MSE-Mean Squared Error
##  [1,]            3      43039             0.353            0.041614864
##  [2,]           69     106730             0.875            0.011796193
##  [3,]          136     118108             0.969            0.008520257
##  [4,]          202     123269             1.011            0.006924794
##  [5,]          268     125895             1.032            0.006001828
##  [6,]          334     126415             1.037            0.005242017
##  [7,]          400     125970             1.033            0.004540799
##  [8,]          467     123963             1.017            0.003143379
##  [9,]          533     121933             1.000            0.002289563

So in my task I used PCA for Dimension Reduction. You can see bulur and clear version of an image, then we creat our palette and we saw the most used color in an image. We use PCC and by using Mean Squared Error we reduced and made it clear.

Thank you!