This question already has answers here:
extract RGB channels from a jpeg image in R
(3 answers)
Closed 6 years ago.
I have a jpeg image that I am attempting to extract the RGB values from in R.
Here is the image:
I am able to access the pixel values quite easily with the following code:
library(jpeg)
y <- readJPEG("MOLD_1.jpg")
head(y)
This returns:
[1] 0.9450980 0.9450980 0.9450980 0.9490196 0.9490196 0.9529412
I'm interested in knowing the color values associated with those pixels. I've tried to use alot of packages to figure this out including raster, pixmap, etc.
I'm struggling pretty bad - any help would be appreciated.
readJPEG returns a 3-D array that is height x width x channels. You can access individual color values using standard indexing. For example, y[,,1] will give you a height x width matrix of red intensities. You can convert these to color values using the rgb() function:
val <- rgb( y[,,1], y[,,2], y[,,3] )
myImg <- matrix( val, dim(y)[1], dim(y)[2] )
Related
I am learning graphical analysis using R. Here is the code, which I can not understand.
barplotVS <- barplot(table(mtcarsData$vs), xlab="Type of engine")
text(barplotVS,table(mtcarsData$vs)/2,table(mtcarsData$vs),cex=1.25)
The output is like below. I can not understand the function of text(), I googled the text() function, which shows that the parameter of text(x,y) is numeric vectors of coordinates where the text labels should be written. Can anyone tell me what is barplotVS,table(mtcarsData$vs)/2,table(mtcarsData$vs),cex=1.25 in my code.
barplotVS <- barplot(table(mtcarsData$vs), xlab="Type of engine")
print(barplotVS)
outputs:
[,1]
[1,] 0.7
[2,] 1.9
These are the positions where the center of the bars in the barplot are on the x axis.
print(table(mtcarsData$vs))
outputs:
0 1
18 14
the numbers below are the occurrences of each value that is present in mtcarsData$vs and the numbers above are the actual value that is counted.
When you run the function:
text(barplotVS,table(mtcarsData$vs)/2,table(mtcarsData$vs),cex=1.25)
the first value will be the x positions where to put the labels (i.e. 0.7 and 1.9), the second parameter will be the y positions set in this case to total counts divided by two (i.e. 9 and 7) meaning to put the labels halfway in the bars, the third will be the labels (i.e. 18 and 14) and finally cex is a value that allows to change the size of the font.
Anyway R has in general a good documentation that you can call by using the ? operator (as suggested in the comments). In order to understand try to run the code and check what each variable contains with print or str functions. If you use a IDE (e.g. RStudio) have the content of the variables in a graphical panel so you don't event need to print.
This question already has an answer here:
How to find changing points in a dataset
(1 answer)
Closed 5 years ago.
enter image description here
enter image description here
Kindly request to refer to the images to get a complete understanding
I have a huge dataset with numeric values. I would need to find the points at which an increasing or decreasing trend starts and ends.
E.g:
[100312
100317
100380
100432
100438
100441
100509
100641
100779
100919
100983
100980
100978
100983
100986
100885
100767
100758
100755
100755]
I have shown 5000 of the 1 million rows I have in my data.
Output > 100317(starting point of increase),100432 (end point of increase), 100441 (starting point of increase) 100919(end point of increase).
A change of ~10 is considered as noise.
you can try this code; starting point of increase and ending point of increase
df <- c(100312,100317,100380,100432,100438,100441,100509,100641,100779,100919,100983,100980,100978,100989,100999,100885,100767,100758,100755,100755)
indexs <- which(diff(df) >= 10)
flag <- which(diff(indexs) > 1)
end <- c(flag, length(indexs))
start <- c(1, end[-length(end)] + 1)
mapply(function(x, y) c(df[indexs[x]], df[indexs[y]]), start, end)
I am trying to create some lines on a graph based on a third coordinate (x,y, temp). I would like to get a vector of indexes so I can split them into x and y vectors for each duplicate temperature. To make this more clear, I will include my actual data set:
DataFrame
I am trying to make multiple lines that have the same temp value. For example, I would like to have the following coordinates on the same line [0,14] [0,22] [0,26] [0,28]. They all have the temp value of 5.8. Once I find the duplicates, I will record the indexes in a vector which will allow me to retrieve the x and y coordinates. One other aspect is that I will not always know how many entries are going to be in the data.frame.
My question is how can I find the duplicates and store their indices in a vector? Once I have the indices for the duplicate temps, I can be sure to grab their x y coordinates and use that to create lines.
If you can answer my question or have any advice on how I can do this better, all help is appreciated
Consider the following:
df <- data.frame(temp = sample.int(n=3, size=5, replace=T))
df
temp
1 3
2 3
3 1
4 3
5 1
duplicated(df$temp)
[1] FALSE TRUE FALSE TRUE TRUE
which(duplicated(df$temp))
[1] 2 4 5
You've stated in the comments that you're looking to make an isopleth graph. The procedure you have described will not generate anything resembling an isopleth graph. Since it looks like your data is arranged in a regular grid, you should do something like the solutions presented in this question and answer, which use functions specifically designed for extracting contours from a grid of values. Another option is the contourLines function in the gDevices package. If you want higher-resolution, less jagged contours, you might look into using either the interp.surface or Krig functions from the fields package to interpolate your data to the resolution you require.
I'm currently doing a classification project and the data I'm using includes lat/long attributes. In order to simply the model(s) I'm thinking it might be easier to replace the raw coordinates with a single column of 'grid' numbers.
By this I mean chop-up the area that the coordinates cover into an arbitrary number of grid points, number each square within the grid, and then replace the lat/long figures with the grid number which they fall in. For example, a 9 square grid might look like this:
123
456
789
I've done a fair bit of searching on here and Google and can't seem to find a solution. The closest I can find is the Universal Transverse Mercator coordinate system (which some R packages support), but the squares within this grid are too large. I'd like to be able to set the size of the grid myself.
I'm at a bit of a loss, and was wondering if the kind people of this forum knew of any R packages or techniques to achieve what I'd like. I'll append an example of my lat/long columns. Thanks.
Latitude Longitude
41.95469 -87.800991
41.95469 -87.800991
41.994991 -87.769279
41.974089 -87.824812
41.974089 -87.824812
41.9216 -87.666455
41.891118 -87.654491
41.867108 -87.654224
41.867108 -87.654224
41.896282 -87.655232
41.919343 -87.694259
Not especially elegant, but this works
pos <- data.frame(lat=c(
41.95469,
41.95469,
41.994991,
41.974089,
41.974089,
41.9216,
41.891118,
41.867108,
41.867108,
41.896282,
41.919343),
long=c(
-87.824812,
-87.769279,
-87.800991,
-87.800991,
-87.824812,
-87.666455,
-87.654491,
-87.654224,
-87.654224,
-87.655232,
-87.694259))
gridx <- seq(from=-87.9,to=-87.6,by=0.01)
gridy <- seq(from=41.8,to=42,by=0.01)
xcell <- unlist(lapply(pos$long,function(x) min(which(gridx>x))))
ycell <- unlist(lapply(pos$lat,function(y) min(which(gridy>y))))
pos$cell <- (length(gridx) - 1) * ycell + xcell
I have an image of columns of red and blue bordered circles like so:
Where the columns alternate red and blue (in this example the first column is red)
I have been able to create a raster brick and plot the image in RGB layers but I want to count these columns into a vector like this (from above example). Values 1(red) and 2(blue)
1,1,1,1,2,2,2,1,1,2,1,1,1 ...
Is it possible to clear out areas of the brick I don't need for counting and collapse the brick down into values I could then convert into the numbers or labels I want? Or is there a much simpler way that I'm unable to locate? Also long term I want to be able to point the program at several images without opening them myself.
Edit: To clear somethings up, I want to count the circles top to bottom, left to right. For example once the first col is counted, I want to start over at the top of the next column on the right. Also I'm not sure if I'm headed in the right direction but I was able to remove all background cells from the image. leaving me with a plot of only values where the circles are.
Edit 2:
The current code I have for the image above.
color.image <- brick("image")
color.image = dropLayer(color.image,4) #gets rid of a channel
plot(color.image)
e <- extent(-10, 240, 45, 84.8) #xmin,xmax, ymin,ymax
ccolor.image <- crop(color.image, e)
plot(ccolor.image)
#thresholding to simplify what I was dealing with
mini=ccolor.image[ccolor.image > 97] = NA
mini=ccolor.image[ccolor.image < 15] = NA
mini=ccolor.image[ccolor.image > 20] = 80
plot(ccolor.image)
mcolor = as.matrix(ccolor.image)
colSums(ccolor.image)
rowSums(ccolor.image)
Edit 3:
I figured it out! Or at least found a round about way to do it, will post code later once I clean it up some. I still however would like input on creating a vector based on the matrix of values I have for my simplified raster brick matrix. Code coming soon!
The fastest way to count values in a raster is freq(x, merge=T). This will give you the value in one column and the frequency in as many columns as you have rows. In this way we the need to poll a value of interest and sum all the other columns (the counts). Hope that helps!
freq_vals <- freq ( rasterbrick , merge = T )
sum( freq_vals [ which ( freq_vals$value == 1 ) , 2 : ncol ( freq_vals ) ] )