transform dataframe to json structure - r

Need help with converting this df to exact JSON as an example using R. Already tried a lot of approaches but cant succeed. Please help.
Code for generating sample:
df <- data.frame(month = c(1, 1, 1, 2, 2, 2),
station = c('AE', 'DС', 'CL', 'AE', 'DC', 'CL'),
persons = c(3, 12, 21, 12, 10, 9),
results = c(10, 34, 57, 19, 16, 5)
)
Its needed to drop column "station" and add level "summary" which gather results to pairs "person" and "results" just as like example shows.
Needed JSON output.
[
{
"month": "1",
"summary": [
{
"persons": 3,
"results": 10
},
{
"persons": 12,
"results": 34
},
{
"persons": 21,
"results": 57
}
]
},
{
"month": "2",
"summary": [
{
"persons": 12,
"results": 19
},
{
"persons": 10,
"results": 16
},
{
"persons": 9,
"results": 5
}
]
}
]

You could use tidyr::nest and jsonlite::toJson like so:
library(tidyr)
library(dplyr)
library(jsonslite)
df |>
select(-station) |>
group_by(month) |>
nest() |>
rename(summary = data) |>
jsonlite::toJSON()
#> [{"month":1,"summary":[{"persons":3,"results":10},{"persons":12,"results":34},{"persons":21,"results":57}]},{"month":2,"summary":[{"persons":12,"results":19},{"persons":10,"results":16},{"persons":9,"results":5}]}]

Related

Convert DataFrame to JSON with single array

Let's say I have the following data....
areaId <- "abc123"
time <- format( seq.POSIXt(as.POSIXct(Sys.Date()), as.POSIXct(Sys.Date()+1), by = "5 min"),"%Y-%m-%d %H:%M:%S", tz="GMT")
value <- 10
df <- data.frame(areaId, time, value)
Giving output
$ areaId <chr> "abc123", "abc123", "abc123", "abc123", "abc123", "abc123", "abc123", "abc123", "abc123", "abc123", "abc123", "abc12…
$ time <chr> "2022-01-30 00:00:00", "2022-01-30 00:05:00", "2022-01-30 00:10:00", "2022-01-30 00:15:00", "2022-01-30 00:20:00", "…
$ value <dbl> 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, …
How can I convert into a JSON file that looks like this so I can POST to an API... everything I've tried so far gives me 3 individual arrays rather than 1.
{
"nameofdata": [
{
"areaId": "abc123",
"time": "2022-01-30T00:00:00Z",
"value": 0,
},
{
"areaId": "abc123",
"time": "2022-01-30T00:05:00Z",
"value": 0,
},
{
"areaId": "abc123",
"time": "2022-01-30T00:10:00Z",
"value": 0,
},
...
]
}
Many thanks for any assistance.
You can do:
library(jsonlite)
toJSON(list(nameofdata = df), pretty = TRUE)
which gives:
{
"nameofdata": [
{
"areaId": "abc123",
"time": "2022-01-30 00:00:00",
"value": 10
},
{
"areaId": "abc123",
"time": "2022-01-30 00:05:00",
"value": 10
},
{
"areaId": "abc123",
"time": "2022-01-30 00:10:00",
"value": 10
}
…
]
}

Split Column in 3 columns with R

I'm trying to separate a column into 3 columns.
My code:
library(dplyr)
library(tidyr)
table1 <- read.csv("tablepartipants.csv")
table2 <- tidyr::separate(table1, col = unique_participant, into = c("uID", "gender", "employment"), sep='.')
I always get this error: Expected 3 pieces. Additional pieces discarded in 80 rows [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, ...].
This is how the column dataset looks like
All 3 "new" columns are empty...
Remove the sep part of your command. A period is the default and . is a special character.
# Example data.frame
table1 <- data.frame(unique_participant = paste0(30:33, c('.male.Student', '.female.Student')))
One option
separate(table1, unique_participant, into = c("uID", "gender", "employment"))
Or using \\. to specify a period.
separate(table1, unique_participant, into = c("uID", "gender", "employment"), sep = '\\.')

Nested R dataframe to JSON with objects instead of arrays

I need to convert a dataframe to JSON. There are several nested dataframes as variables in the dataframe to convert to JSON.
But, when converting to JSON, I need the data for Values1 described below to be an object (enclosed in {} only) instead of an array (enclosed in []).
The code below is a reprex to show my current workflow and problem.
library(dplyr)
library(tidyr)
library(jsonlite)
df1 <- data.frame(name = c("a", "b", "c"),
v = c(1, 2, 3),
w = c(10, 20, 30)) %>%
group_by(name) %>%
nest_legacy(.key = "Values1")
df2 <- data.frame(name = c("a", "b", "c"),
x = c(5, 10, 15),
y = c(100, 200, 300),
z = c(1000, 2000, 3000)) %>%
group_by(name) %>%
nest_legacy(.key = "Values2")
df3 <- df1 %>%
left_join(df2)
json <- toJSON(df3, dataframe = "rows", pretty = TRUE)
json
This is what the json from the above looks like:
> json
[
{
"name": "a",
"Values1": [
{
"v": 1,
"w": 10
}
],
"Values2": [
{
"x": 5,
"y": 100,
"z": 1000
}
]
},
{
"name": "b",
"Values1": [
{
"v": 2,
"w": 20
}
],
"Values2": [
{
"x": 10,
"y": 200,
"z": 2000
}
]
},
{
"name": "c",
"Values1": [
{
"v": 3,
"w": 30
}
],
"Values2": [
{
"x": 15,
"y": 300,
"z": 3000
}
]
}
]
But, this is what I need it to look like:
> json
[
{
"name": "a",
"Values1": {
"v": 1,
"w": 10
},
"Values2": [
{
"x": 5,
"y": 100,
"z": 1000
}
]
},
{
"name": "b",
"Values1": {
"v": 2,
"w": 20
},
"Values2": [
{
"x": 10,
"y": 200,
"z": 2000
}
]
},
{
"name": "c",
"Values1": {
"v": 3,
"w": 30
},
"Values2": [
{
"x": 15,
"y": 300,
"z": 3000
}
]
}
]
Any ideas how to convert Values1 from arrays to objects? They cannot be in arrays as the API does not accept the [.
I have looked at using unbox() from jsonlite but this only works on singletons. I have also tried to construct my final dataframe in various ways.
Any tips/ideas greatly appreciated!
This should return what you desire:
...
df3 <- left_join(df1, df2, by = "name")
json <- mutate(df3, Values1 = purrr::map(Values1, as.list)) %>%
jsonlite::toJSON(auto_unbox = TRUE, pretty = TRUE)
Can you confirm?

How to create a stacked bar graph in kibana?

I have data in JSON format like this in my elasticsearch:
{
"features": [
{
"feature": "A",
"Yes": 19,
"No": 0,
"Maybe": 81
},
{
"feature": "B",
"Yes": 0,
"No": 0,
"Maybe": 100
},
{
"feature": "C",
"Yes": 10,
"No": 32,
"Maybe": 58
}
]
}
From this, is it possible to obtain a stacked chart as follows?

amchart add labels in between grids

I need to add labels with difference of 10 in both axis( one each between the grid ), WITHOUT compromising the present number of grids.So the number of grid lines should stay 11 and number of labels will go up to 21. Hope that clears my query.Above is my chart, and this is the code -
var chart = AmCharts.makeChart("chartdiv", {
"type": "xy",
"dataProvider": json,
"valueAxes":
[
{
"id":"my_y",
"autoGridCount": false,
"position": "right",
"tickLength":0,
"gridThickness":0.25,
"minimum":-100,
"maximum":100,
"gridCount": 11,
"labelFrequency" : 0.5,
"gridColor":"black",
"gridAlpha":0.50,
"labelOffset": -356,
"axisAlpha":0,
"strictGridCount" : true,
},
{
"id":"my_x",
"autoGridCount": false,
"position": "bottom",
"tickLength":0,
"gridThickness": 0.25,
"minimum":-100,
"maximum":100,
"gridCount": 11,
"labelFrequency" : 0.5,
"gridColor":"black",
"gridAlpha":0.50,
"labelOffset": -320,
"axisAlpha":0,
},
],
"borderAlpha" : 0,
"startDuration": 0,
"legend":[{
"useGraphSettings": false,
"verticalGap":0,
}],
"guides":[
{
"fillAlpha": 0.10,
"value": -100,
"toValue": 100,
}
],
"graphs":
[
{
"id":"g1",
"lineColor": "#FF6600",
"bulletBorderThickness": 1,
"hideBulletsCount": 30,
"animationDuration":0,
"balloonText": "[[value]]",
"bullet": "circle",
"lineAlpha": 0,
"valueField": "value",
"xField": "x",
"yField": "y",
"fillAlphas": 0,
"bulletBorderAlpha": 0,
"minBulletSize": 30,
"maxBulletSize": 30,
"labelText":"[[x]]",
"labelPosition":"inside",
"markerType" : "none",
"switchable":false,
},
],
"marginLeft": 20,
"marginBottom": 20,
"export": {
"enabled": true,
"menu" : [],
},
});
PS : I tried to change the labelFrequency value but I don't think it takes values below 1.
You're right to assume that labelFrequency can't be set to anything lower than 1, or a non-integer for that matter.
The only workaround I can think of is to increase gridCount to the number which displays labels in increments that you want. I.e. 21.
Then disable grid lines altogether. (gridAlpha: 0)
And finally use guides to display lines at values that you need lines displayed at. I.e.:
{
"id": "my_y",
"autoGridCount": false,
"position": "right",
"tickLength": 0,
"gridThickness": 0.25,
"minimum": -100,
"maximum": 100,
"gridCount": 21,
"labelFrequency": 0.5,
"gridColor": "black",
"gridAlpha": 0,
"labelOffset": -356,
"axisAlpha": 0,
"strictGridCount": true,
"guides": [
{ "value": 80, "lineAlpha": 0.5 },
{ "value": 60, "lineAlpha": 0.5 },
{ "value": 40, "lineAlpha": 0.5 },
{ "value": 20, "lineAlpha": 0.5 },
{ "value": 0, "lineAlpha": 0.5 },
{ "value": -20, "lineAlpha": 0.5 },
{ "value": -40, "lineAlpha": 0.5 },
{ "value": -60, "lineAlpha": 0.5 },
{ "value": -80, "lineAlpha": 0.5 }
]
}

Resources