Getting list of attributes inside a JSON - jsonpath

Is it possible to get list of attributes of a particular JSON map with a JSONPath expression? For example:
{"foo": 1, "bar": 2} => ["foo","bar"]

You can use the following code:
Object.getOwnPropertyNames({"foo": 1, "bar": 2})
Here's a link for further information.

Loop through each json object get all the keys and push then into an array. You can try this:
var data=[{"foo": 1, "bar": 2},{"foo1": 1, "bar1": 2}];
var array=[];
$.each(data, function(key, value){
var item;
item=Object.keys(value);
array.push(item);
});
console.log(array);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

Related

Nested maps in Golang

func main() {
var data = map[string]string{}
data["a"] = "x"
data["b"] = "x"
data["c"] = "x"
fmt.Println(data)
}
It runs.
func main() {
var data = map[string][]string{}
data["a"] = append(data["a"], "x")
data["b"] = append(data["b"], "x")
data["c"] = append(data["c"], "x")
fmt.Println(data)
}
It also runs.
func main() {
var w = map[string]string{}
var data = map[string]map[string]string{}
w["w"] = "x"
data["a"] = w
data["b"] = w
data["c"] = w
fmt.Println(data)
}
It runs again!
func main() {
var data = map[string]map[string]string{}
data["a"]["w"] = "x"
data["b"]["w"] = "x"
data["c"]["w"] = "x"
fmt.Println(data)
}
But it fails!?
Is there a problem with nested maps in Go? Or is there no multiple bracket support for nested maps?
The zero value for map types is nil. It is not yet initialized. You cannot store values in a nil map, that's a runtime panic.
In your last example you initialize the (outer) data map, but it has no entries. When you index it like data["a"], since there is no entry with "a" key in it yet, indexing it returns the zero value of the value type which is nil for maps. So attempting to assign to data["a"]["w"] is a runtime panic.
You have to initialize a map first before storing elements in it, for example:
var data = map[string]map[string]string{}
data["a"] = map[string]string{}
data["b"] = make(map[string]string)
data["c"] = make(map[string]string)
data["a"]["w"] = "x"
data["b"]["w"] = "x"
data["c"]["w"] = "x"
fmt.Println(data)
Output (try it on the Go Playground):
map[a:map[w:x] b:map[w:x] c:map[w:x]]
Note that when you declare a variable of map type and initialize it with a composite literal (as in var data = map[string]string{}), that also counts as initializing.
Note that you may also initialize your nested maps with a composite literal:
var data = map[string]map[string]string{
"a": map[string]string{},
"b": map[string]string{},
"c": map[string]string{},
}
data["a"]["w"] = "x"
data["b"]["w"] = "x"
data["c"]["w"] = "x"
fmt.Println(data)
Output is the same. Try it on the Go Playground.
While the most straightforward answer to this question is to initialize your nested maps as previously described, there is another potential option depending on your access pattern. If you need a truly hierarchical system of maps, then the previous answers are just fine. However, if you simply need to look up values in the map using multiple facets, read on!
It is totally acceptable for maps to use structs as keys (in fact, anything that is comparable can be used). Thus, you can use a single map with struct keys like this example from the Golang blog, which is a hit counter that tracks page hits by country:
type Key struct {
Path, Country string
}
hits := make(map[Key]int)
// set: Vietnamese person visiting the home page
hits[Key{"/", "vn"}]++
// get: see how many Chinese persons read the spec
n := hits[Key{"/ref/spec", "cn"}]
I don't see maps like this often enough, instead many people reach for the nested variant first, which I think may not always be the right fit.
In addition to icza's answer. Map initialization can be written in short form:
var data = map[string]map[string]string{
"a": map[string]string{
"w": "x"},
"b": map[string]string{
"w": "x"},
"c": map[string]string{
"w": "x"},
"d": map[string]string{},
}
fmt.Println(data)
Output is the same. Try it on the Go Playground. The key "d" added to demonstrate the mapping with an empty map.
The below solution might be useful for you.
var data = map[string]interface{}{
"publishInfo": map[string]interface{}{
"title": publishInfo.Title,
"description": publishInfo.Desc,
"thumbnail": publishInfo.ImageSrc,
"url": publishInfo.URL,
"tags": publishInfo.Tags,
},
"revision": draftInfo.Revision,
}

Swift Remove element from an array and then remove the same element from an array inside of a dictionary

So I have a struct and a dictionary that look like this:
struct minStruct {
var labelText:String?
var descText:String?
var imaginator:UIImage?
var rea:String?
var url:NSURL?}
var dict = [String:[minStruct]]()
Thus, I have a dictionary with the value as an array of structs. In my application I create an array of all the structs inside the dictionary to be able to show the structs in a tableView, which is done by this code:
let dictValues = Array(dict.values)
let dictFlat = Array(dictValues.flatten())
The new array dictFlat is used for populating the tableView, as it contains every struct that was contained inside of the original dictionary. If I would like to remove a struct from the tableView, i would of course remove it from the array dictFlat, however I need to remove the same struct from the original dictionary (dict) to achieve what I want. So my question is simply how to remove the same struct that is deleted from the array dictFlat from the dictionary dict. To clarify, you could you this example:
dict = ["Food":[minStruct(labelText: "this is a string", descText: "Also a string", imaginator: UIImage(named: "image-name")!, rea: "also a string", url: NSURL(string: "https://www.google.com")]]
Now dictFlat will contain the struct displayed inside of dict above, and now I want to delete that struct from both. Using swipe to delete from the tableView, the only struct that will be deleted is the one inside of dictFlat (using the indexPath to delete just as you would usually do when deleting from a tableView). Now I want to delete the same item which was deleted from dictFlat and also from the tableView, from the original dictionary (dict). So what I want is to check if dict contains the struct that was deleted from dictFlat, and if it does contain it, it shall be deleted.
I hope that I was clear enough, thanks in advance!
What is the trouble? See the example, I used there [Int] as a value, but it could be anything else
var dict:[String:[Int]] = [:]
let arr0 = [1,2,3,4,5]
let arr1 = [2,3,4,5,6]
dict["arr0"] = arr0
dict["arr1"] = arr1
// working copy
var arr = dict["arr0"] ?? []
// remove one value
arr.removeAtIndex(2)
// update your dictionary
dict["arr0"] = arr
print(dict) // ["arr1": [2, 3, 4, 5, 6], "arr0": [1, 2, 4, 5]]

Kotlin's List missing "add", "remove", Map missing "put", etc?

In Java we could do the following
public class TempClass {
List<Integer> myList = null;
void doSomething() {
myList = new ArrayList<>();
myList.add(10);
myList.remove(10);
}
}
But if we rewrite it to Kotlin directly as below
class TempClass {
var myList: List<Int>? = null
fun doSomething() {
myList = ArrayList<Int>()
myList!!.add(10)
myList!!.remove(10)
}
}
I got the error of not finding add and remove function from my List
I work around casting it to ArrayList, but that is odd needing to cast it, while in Java casting is not required. And that defeats the purpose of having the abstract class List
class TempClass {
var myList: List<Int>? = null
fun doSomething() {
myList = ArrayList<Int>()
(myList!! as ArrayList).add(10)
(myList!! as ArrayList).remove(10)
}
}
Is there a way for me to use List but not needing to cast it, like what could be done in Java?
Unlike many languages, Kotlin distinguishes between mutable and immutable collections (lists, sets, maps, etc). Precise control over exactly when collections can be edited is useful for eliminating bugs, and for designing good APIs.
https://kotlinlang.org/docs/reference/collections.html
You'll need to use a MutableList list.
class TempClass {
var myList: MutableList<Int> = mutableListOf<Int>()
fun doSomething() {
// myList = ArrayList<Int>() // initializer is redundant
myList.add(10)
myList.remove(10)
}
}
MutableList<Int> = arrayListOf() should also work.
Defining a List collection in Kotlin in different ways:
Immutable variable with immutable (read only) list:
val users: List<User> = listOf( User("Tom", 32), User("John", 64) )
Immutable variable with mutable list:
val users: MutableList<User> = mutableListOf( User("Tom", 32), User("John", 64) )
or without initial value - empty list and without explicit variable type:
val users = mutableListOf<User>()
//or
val users = ArrayList<User>()
you can add items to list:
users.add(anohterUser) or
users += anotherUser (under the hood it's users.add(anohterUser))
Mutable variable with immutable list:
var users: List<User> = listOf( User("Tom", 32), User("John", 64) )
or without initial value - empty list and without explicit variable type:
var users = emptyList<User>()
NOTE: you can add* items to list:
users += anotherUser - *it creates new ArrayList and assigns it to users
Mutable variable with mutable list:
var users: MutableList<User> = mutableListOf( User("Tom", 32), User("John", 64) )
or without initial value - empty list and without explicit variable type:
var users = emptyList<User>().toMutableList()
//or
var users = ArrayList<User>()
NOTE: you can add items to list:
users.add(anohterUser)
but not using users += anotherUser
Error: Kotlin: Assignment operators ambiguity:
public operator fun Collection.plus(element: String): List defined in kotlin.collections
#InlineOnly public inline operator fun MutableCollection.plusAssign(element: String): Unit defined in kotlin.collections
see also:
https://kotlinlang.org/docs/reference/collections.html
Agree with all above answers of using MutableList but you can also add/remove from List and get a new list as below.
val newListWithElement = existingList + listOf(element)
val newListMinusElement = existingList - listOf(element)
Or
val newListWithElement = existingList.plus(element)
val newListMinusElement = existingList.minus(element)
Apparently, the default List of Kotlin is immutable.
To have a List that could change, one should use MutableList as below
class TempClass {
var myList: MutableList<Int>? = null
fun doSomething() {
myList = ArrayList<Int>()
myList!!.add(10)
myList!!.remove(10)
}
}
Updated
Nonetheless, it is not recommended to use MutableList unless for a list that you really want to change. Refers to https://hackernoon.com/read-only-collection-in-kotlin-leads-to-better-coding-40cdfa4c6359 for how Read-only collection provides better coding.
In Kotlin you must use MutableList or ArrayList.
Let's see how the methods of MutableList work:
var listNumbers: MutableList<Int> = mutableListOf(10, 15, 20)
// Result: 10, 15, 20
listNumbers.add(1000)
// Result: 10, 15, 20, 1000
listNumbers.add(1, 250)
// Result: 10, 250, 15, 20, 1000
listNumbers.removeAt(0)
// Result: 250, 15, 20, 1000
listNumbers.remove(20)
// Result: 250, 15, 1000
for (i in listNumbers) {
println(i)
}
Let's see how the methods of ArrayList work:
var arrayNumbers: ArrayList<Int> = arrayListOf(1, 2, 3, 4, 5)
// Result: 1, 2, 3, 4, 5
arrayNumbers.add(20)
// Result: 1, 2, 3, 4, 5, 20
arrayNumbers.remove(1)
// Result: 2, 3, 4, 5, 20
arrayNumbers.clear()
// Result: Empty
for (j in arrayNumbers) {
println(j)
}
UPDATE: As of Kotlin 1.3.70, the exact buildList function below is available in the standard library as an experimental function, along with its analogues buildSet and buildMap. See https://blog.jetbrains.com/kotlin/2020/03/kotlin-1-3-70-released/.
Confining Mutability to Builders
The top answers here correctly speak to the difference in Kotlin between read-only List (NOTE: it's read-only, not "immutable"), and MutableList.
In general, one should strive to use read-only lists, however, mutability is still often useful at construction time, especially when dealing with third-party libraries with non-functional interfaces. For cases in which alternate construction techniques are not available, such as using listOf directly, or applying a functional construct like fold or reduce, a simple "builder function" construct like the following nicely produces a read-only list from a temporary mutable one:
val readonlyList = mutableListOf<...>().apply {
// manipulate your list here using whatever logic you need
// the `apply` function sets `this` to the `MutableList`
add(foo1)
addAll(foos)
// etc.
}.toList()
and this can be nicely encapsulated into a re-usable inline utility function:
inline fun <T> buildList(block: MutableList<T>.() -> Unit) =
mutableListOf<T>().apply(block).toList()
which can be called like this:
val readonlyList = buildList<String> {
add("foo")
add("bar")
}
Now, all of the mutability is isolated to one block scope used for construction of the read-only list, and the rest of your code uses the read-only list that is output from the builder.
You can do with create new one like this.
var list1 = ArrayList<Int>()
var list2 = list1.toMutableList()
list2.add(item)
Now you can use list2, Thank you.
https://kotlinlang.org/docs/reference/collections.html
According to above link List<E> is immutable in Kotlin.
However this would work:
var list2 = ArrayList<String>()
list2.removeAt(1)
A list is immutable by Default, you can use ArrayList instead. like this :
val orders = arrayListOf<String>()
then you can add/delete items from this like below:
orders.add("Item 1")
orders.add("Item 2")
by default ArrayList is mutable so you can perform the operations on it.
In concept of immutable data, maybe this is a better way:
class TempClass {
val list: List<Int> by lazy {
listOf<Int>()
}
fun doSomething() {
list += 10
list -= 10
}
}

Having a second helper call inside a helper, overwrites the first helper value in handlebars

If I have helpers like:
Handlebars.registerHelper("testHelper", function (v) {
console.log(v);
}
Handlebars.registerHelper("testHelper2", function (v) {
return v;
}
and have two subhelpers like:
{{testHelper first=(testHelper2 '1') second=(testHelper2 '2')}}
both first and second are returning '2'. The console output is:
data: {},
hash: {
first: '2',
second: '2'
}
How would I make it return the correct values? If I do the following it returns first as 1:
{{testHelper first=(testHelper2 '1')}}
Does anyone have a workaround for this? Please note that I made the helpers simple and wouldn't use a helper to return the same value normally.
Here is a fiddle example.
The only way that I see is to not use a hash as parameter for first helper. Instead of it use arguments directly.
Helper:
Handlebars.registerHelper("testHelper", function () {
var args = Array.prototype.slice.call(arguments, 0);
return 'first: '+args[0]+' second: '+args[1];
});
Template:
{{testHelper (testHelper2 '1') (testHelper2 '2')}}
Fiddle.

Pass array written in template to meteor/handlebars helper

I have a helper called printArray that just prints every item in an array. It works great when I define the array in JS and pass it in to the helper via a context object. What I want to do is define the array right in the template, like:
{{printArray arr=[1, 3, 4] }}
Unfortunately, by the time this gets to my helper, the arr key points to undefined. Is there any valid syntax to get the array inside my helper without defining it in javascript?
You can use JavaScript's arguments array to accomplish something like this. The arguments array gives you access to every value passed to the function when it is called.
This will allow you to use syntax like this:
{{printArray 1 3 4}}
The code looks like this:
Handlebars.registerHelper('printArray', function() {
//Last argument is the options object.
var options = arguments[arguments.length - 1];
//Skip the last argument.
for(var i = 0; i < arguments.length - 1; ++i) {
//Do your thing with each array element.
}
//Return your results...
return '';
});
You can almost accomplish this with the use of eval(), using a helper like this:
Handlebars.registerHelper('printArray', function(values) {
var array = eval(values);
if (array.constructor === Array()) {
...
}
}
The above allows you to call this from the template:
{{printArray '[0, 1, 2]'}}
The one caveat to this method is that you have to pass your array as a string.
You need to use another helper that returns an array
Template.ArrayDemo.helpers({
arrayValues: [1, 2, 3],
printArray: function(arr) {
for (i = 0; i < arr.length; i++) {
console.log(arr[i]);
}
}
});
now you can do
{{printArray arr=arrayValues}}
Helper:
printArray: (...options) => {
// remove unneeded properties
options.pop();
// return option array
return options;
}
Template:
{{printArray "banana" "apple" "orange" "kiwi"}}
Returns:
["banana", "apple", "orange", "kiwi"]
You can use it in conjunction with other helpers:
{{#each (printArray "banana" "apple" "orange" "kiwi")}}
{{this}}
{{/each}}
Have you tried passing in just the bracketed value of the array?
{{printArray [1, 3, 4]}}
I know you can easily pass in objects, as arguments to the handlebars helper methods:
{{printArray {arr: [1, 3, 4]} }}
Take a look at these awesome helper methods, most of which I stole from elsewhere, a few of which I wrote or tweaked... They are my reference starting point on the topic:
https://github.com/zeroasterisk/Presenteract/blob/master/client/lib/handlebar-helpers.js
You can define a array helper as below.
Handlebars.registerHelper('array', function() {
return Array.prototype.slice.call(arguments, 0, -1);
}
{{printArray (array 1 3 4)}}
{{printArray '1,3,4'}}
Handlebars.registerHelper("printArray", function(values){
let array = values.split(",");
console.log(array);
});

Resources