How to get position in json file using JS (node.js) - javascript

How do I get position in JSON file like
{
"some-random-id3": {
"totalxp": 981
},
"some-random-id1": {
"totalxp": 654
},
"some-random-id2": {
"totalxp": 547
},
"some-random-id0": {
"totalxp": 10
}
}
I mean, how can i get if i enter "some-random-id2" -> 3. position or "some-random-id3" -> 1. position
I didnt't tried anything bcs I don't know how to do.

There is no defined way of doing this. As the JSON documentation quotes (emphasis added):
An object is an unordered set of name/value pairs.
You might be able to get away with iterating through Object.keys(), but JS objects are also unordered and it is not required to give it to you in the same order every time.
If you're willing to break the JSON specification, then your best bet is to implement your own JSON parser using the Map type, which preserves insertion order. However, this will likely be quite the project. Your other option is to change your data structure. You may want to consider using an array instead (which preserves order), like this:
[{
id: "some-random-id3",
value: {
"totalxp": 981
}
},
{
id: "some-random-id1",
value: {
"totalxp": 654
}
},
{
id: "some-random-id2",
value: {
"totalxp": 547
}
},
{
id: "some-random-id0",
value: {
"totalxp": 10
}
}
]

Related

mongoDB - Regex search against partial field values

I've a collection of countries with country calling code in the country object. How can I find a country using calling code with a mobile number?
const countries = [
{
name: 'UAE',
callingCode: 971
},
{
name: 'USA',
callingCode: 1
},
{
name: 'UK',
callingCode: 44
}
];
const number = '971524500000'; // Input
How can I find country for the given mobile using regex in mongoose javascript;
[https://en.wikipedia.org/wiki/List_of_country_calling_codes][1]
Take a look at the link above on country calling codes, and specifically see the section "Tree List".
One solution would be to implement a schema in Mongo based on this tree in order to decode the country codes.
So, a table could be created to store Mongo documents containing a field "1x" "2x" "21x" etc (the Y axis in the Tree List table).
Each of these documents could contain an array of sub-documents from x=0 to x=9 (the x axis in the Tree List table). The sub-document can contain the country name/code you are looking for. You can use a direct index into the array in the Mongo document for an efficient lookup.
I think you'll find this to be a pretty efficient implementation and should cover all the bases.
If you can restructure your array to an object this would be the fastest
const countries =
{
971: 'UAE',
1: 'USA',
44: 'UK',
}
;
var code = 44;
console.log(countries[code]);
const countries = [
{
name: 'UAE',
callingCode: 971
},
{
name: 'USA',
callingCode: 1
},
{
name: 'UK',
callingCode: 44
}
];
var myFound =countries.filter(myFunc.bind(this,44));
function myFunc(code,element) {
if(element.callingCode == code){
return element;
}
}
console.log(myFound);
On MongoDB v 4.2 - you can use $let & $regexFind to do this :
db.collection.aggregate([
{
$match: {
$expr: {
$eq: [
{
$let: {
vars: {
value: {
$regexFind: {
input: "971524500000", // pass in as string
regex: { $toString: "$callingCode" }
}
}
},
in: "$$value.idx",
}
},
0
]
}
}
}
]);
Test : MongoDB-Playground
Explanation :
General Use-case :
In general regex searches - Will have an input which will be sub-string of actual string, Ex.:-
Actual string in DB : 'We can do it in mongo'
Input : mongo (/mongo/ - will work)
Your Use-case :
From above case as mongo exists in actual string/value of db field then you can get that document, But your case is different :
Actual string in DB : mongo
Input : 'We can do it in mongo'
This doesn't work that way, So using normal /We can do it in mongo/ isn't going help you here (Also doing few tricks with regex). So we need to make a trick to $regexFind operator. Unlike mongo documentation we need take 971524500000 into input field & regex as string value of callingCode field which is vice-versa to what's given in documentation.
So once we do that, We would get something like below :
{
"match" : "971", /** value of callingCode field */
"idx" : 0, /** Index of `971` in '971524500000' */
"captures" : []
},{
"match" : "1",
"idx" : 2,
"captures" : []
},
null /** 3rd doc no match */
As country code has to be at first of given number we need docs where "idx" : 0 - So we're using $let to get index of returned object & checking against 0 & eventually getting respective docs using $match.
Note :
There is something you need to look into, Just in case if you've docs like below :
{
"_id": ObjectId("5e8f67091aa1cc3d2158ade1"),
"name": "USA",
"callingCode": 1.0
},
{
"_id": ObjectId("5e8f67091aa1cc3d2158ade3"),
"name": "somecountry",
"callingCode": 197.0
}
& input is 1971524500000, then this query will bring both docs in result. This will be the case you need to check on. Anyhow I would suggest to try this query, rather than getting all documents for collection to the code & extract required o/p this might be better to do.

Javascript: Construct an object from array of objects based on matching property id's:

still quite new to higher order functions and trying to use them correctly here if possible.
I have a array of objects being returned from an api constructed like so:
[ {"gymId":3467, "halls": [{ "hallId": "25828", "instructorId": 1064,
"slotIds": [2088,2089], "sessionId":8188},
{"hallId": "25848", "instructorId": 1067, "slotIds": [2088,2089], "sessionId": 8188 }]}]
Expected result I want to achieve is to create a list of objects such as this from the array above ...
{2088: [{ "hallId":"25828", "instructorId":1064, "sessionId":8188 },
{ "hallId":"25848", "instructorId":1067, "sessionId":8188 }],
2089: [{ "hallId":"25828", "instructorId":1064, "sessionId":8188 },
{ "hallId":"25848", "instructorId":1067, "sessionId":8188 }]
}
I was thinking something along the lines of this
halls.reduce((acc, hall) => {
hall.slotIdIds.forEach(slotId => {
acc[slotId] = {
//expected object properties as above here.
};
});
return acc;
}, {}),
Problem is when I reduce in this way only one hallId is being returned and not the two matching hall ids where the slots exist.
Bit perplexed as to how to solve this one and would really appreciate any tips.

Native JavaScript Way to Walk up Document Tree When Comparing Objects

I have done some work to do a deep comparison (via Underscore and diff) between two objects (actually a pre-save and post-save version of the same document) in order to isolate the section that is different after a save. Take this document structure as an example:
{
_id: 4d39fe8b23dac43194a7f571,
name: {
first: "Jane",
last: "Smith"
}
services: [
{
service: "typeOne",
history: [
{ _id: 121,
completed: true,
title: "rookie"
},
{ _id: 122,
completed: false,
title: "novice"
}
]
},
{
service: "typeTwo",
history: [
{ _id: 135,
completed: true,
title: "rookie"
},
{ _id: 136,
completed: false,
title: "novice"
}
]
}
]
}
If a new element is added to the history array I'm able to successfully parse out that change.
However, in addition to pulling out this changed section, I also want to be able to effectively walk up from history in order to find the value for service, because I also need to know which of the two services array elements actually changed. Is there a way I can do this with native es6 JavaScript?
If not, is there a library I can use to determine this? Right now I'm able to get the value for "service" via indexing:
if (diff.path[1] === 0) {
targetService = "typeOne";
} else if (diff.path[1] === 1) {
targetService = "typeTwo";
} else if (diff.path[1] === 2) {
targetService = "typeThree";
}
But from my understanding this isn't full proof, because there's no guarantee the order of elements within "services" couldn't change at some point. I suppose this indexing method could work if I could enforce the ordering of the elements within the services array. I'm just not sure if there's a way to do that (open to suggestions if it is possible).
deep-diff gives you the path to this change, something like this:
{
kind: 'N',
path: ['services', 1, 'history'],
// ... other properties
}
You can use this path to track the changed object:
tree.services[changes.path[1]].service // 'typeTwo'

Using jQuery removeData() with nested data

I'm using the jQuery data() function to store data on a series of divs in a format similar to:
{
options: {
example: {
option_1: {
value: "example 1"
},
option_2: {
value: "example 2"
}
}
}
}
I can add new keys and update the data, e.g.
$("#mydiv").data('options',{'example':{} }); // the object is already created in the live version
$("#mydiv").data('options')['example']['option_3'] = { value: "example 3" };
But when I come to use removeData(), FireBug tells me that the key is undefined, e.g.
$("#mydiv").removeData('options')['example']['option_2'];
Any help appreciated!
.removeData(name) removes the previously stored data with the given name, and returns a jQuery object. In your scenario, you don't want the remove the entire options object, just a specific property of it, so you should be using delete instead:
delete $("#mydiv").data('options')['example']['option_2'];

Get object within JSON object only by knowing its position, and not name

I'm currently looking into the Twitter-API - specifically the daily trends-API (http://search.twitter.com/trends/current.json).
Example return from Twitter
{
trends: {
2009-11-19 14:29:16: [
{
name: "#nottosayonfirstdate",
query: "#nottosayonfirstdate"
},
{
name: "New Moon",
query: ""New Moon""
},
{
name: "#justbecause",
query: "#justbecause"
}
]
}
}
I wonder how I can return the values within there without knowing the exact date at the time of the call, since it won't be possible to synchronise the client-time with the server-time.
Normally, I'd go for trends.something[1].name to get the name, but since the timestamp will change all the time, how can I get it when trends is no array?
you can use this:
for (var i in trends) {
alert (i); // "2009-11-19 14:29:16"
alert (trends[i][0].name); // "#nottosayonfirstdate"
}

Categories