find a value in JSON stringify array - javascript

i want to find a value in JSON stringify array
[{"id":"432","temperature":"1","humidity":"1","createat":"0000-00-00 00:00:00"},{"id":"433","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:49:57"},{"id":"434","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:52:02"},{"id":"435","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:55:26"},{"id":"436","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:58:50"},{"id":"437","temperature":"22.00","humidity":"48","createat":"2015-10-11 20:02:14"},{"id":"438","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:23:15"},{"id":"439","temperature":"22.50","humidity":"50","createat":"2015-10-11 21:24:37"},{"id":"440","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:17"},{"id":"441","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:41"}]
my idea to get this value is to know if what i am adding is not already added

// stringified JSON
stringifiedJson = '[{"id":"432","temperature":"1","humidity":"1","createat":"0000-00-00 00:00:00"},{"id":"433","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:49:57"},{"id":"434","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:52:02"},{"id":"435","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:55:26"},{"id":"436","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:58:50"},{"id":"437","temperature":"22.00","humidity":"48","createat":"2015-10-11 20:02:14"},{"id":"438","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:23:15"},{"id":"439","temperature":"22.50","humidity":"50","createat":"2015-10-11 21:24:37"},{"id":"440","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:17"},{"id":"441","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:41"}]';
// parse the stringified JSON into a JavaScript object
parsedJson = JSON.parse(stringifiedJson);
// the object in the array you want to check
number = 0
// check if the property exists
if(typeof parsedJson[number].humidity !== 'undefined') {
// set the property
parsedJson.humidity = 1;
}
// stringify your object again
stringifiedJson = JSON.stringify(parsedJson);
EDIT: here is a propertyExists function:
var propertyExists = function(stringifiedJson, id, property) {
// parse the stringified JSON into a JavaScript object
parsedJson = JSON.parse(stringifiedJson);
// check if the property exists for a given ID
for(var i = 0; i < parsedJson.length; i += 1) {
if(parseInt(parsedJson[i].id) === parseInt(id)) {
return (typeof parsedJson[i][property] !== 'undefined')
}
}
return false;
}
// stringified json
var stringifiedJson = '[{"id":"432","temperature":"1","humidity":"1","createat":"0000-00-00 00:00:00"},{"id":"433","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:49:57"},{"id":"434","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:52:02"},{"id":"435","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:55:26"},{"id":"436","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:58:50"},{"id":"437","temperature":"22.00","humidity":"48","createat":"2015-10-11 20:02:14"},{"id":"438","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:23:15"},{"id":"439","temperature":"22.50","humidity":"50","createat":"2015-10-11 21:24:37"},{"id":"440","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:17"},{"id":"441","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:41"}]';
console.log(propertyExists(stringifiedJson, 432, 'humidity'));

....
var jsonArray = [{"id":"432","temperature":"1","humidity":"1",.....
var isPresent = false;
$.each(jsonArray, function(i,v){
if(jsonArray[i].id == newObject.id){
isPresent = true;
}
});
if(!isPresent){
jsonArray.push(newObject);
}
....

i want to find a value in JSON stringify array
You don't say what value you are trying to find. What you've posted is an Array literal, not JSON. If you want to iterate over the array to determine if it contains an object with a certain property that has a particular value, you can use Array.prototype.some:
function hasPropValue(array, prop, value) {
return array.some(function(obj) {
return obj.hasOwnProperty(prop) && obj[prop] === value;
}
}
some will iterate only over members that exist, and will stop as soon as the callback returns true, otherwise it returns false. If you really do have a string value that is valid JSON, you can do:
hasPropValue(JSON.parse(jsonText), 'id', '432');
var jsonText = '[{"id":"432","temperature":"1","humidity":"1","createat":"0000-00-00 00:00:00"},{"id":"433","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:49:57"},{"id":"434","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:52:02"},{"id":"435","temperature":"22.40","humidity":"48","createat":"2015-10-11 19:55:26"},{"id":"436","temperature":"22.00","humidity":"48","createat":"2015-10-11 19:58:50"},{"id":"437","temperature":"22.00","humidity":"48","createat":"2015-10-11 20:02:14"},{"id":"438","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:23:15"},{"id":"439","temperature":"22.50","humidity":"50","createat":"2015-10-11 21:24:37"},{"id":"440","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:17"},{"id":"441","temperature":"22.50","humidity":"51","createat":"2015-10-11 21:26:41"}]'
function hasPropValue(array, prop, value) {
return array.some(function(obj) {
return obj.hasOwnProperty(prop) && obj[prop] === value;
});
}
document.write(hasPropValue(JSON.parse(jsonText), 'id', '432'));

Related

Recursive javascript function that converts nested object keys to string and store all keys in arrray

I am trying to write a javascript recursive function that receives one parameter - nested JSON object.
The function goes through the potentially infinitely nested object and converts all the keys (property names) to a string that is stored in array. Array is returned to a place where the function was called.
Example of JSON object:
{
OBJECT1: {
ATTRIBUTE3: {
PARAMETER2: {
PROPERTY1: {
}
}
}
}
}
The object does not hold any values.
What i tried and did not work:
function convertKeysToString(obj) {
let keys = [];
for (let key in obj) {
if (typeof obj[key] === 'object') {
keys = keys.concat(convertKeysToString(obj[key]));
} else {
keys.push(key.toString());
}
}
return keys;
}
As a result, I expected that returned key is pushed to an array, but the funciton didnt get the key at all or was not pushed to keys array.
Another code I tried:
function getNestedObjectKeys(obj) {
var keys = []
var firstLevel = null
var property = Object.keys(obj)
property = property[0]
firstLevel = Object.keys(obj[property])[0]
if (firstLevel == undefined) {
return 0
}
let returnedValue = keys.unshift(getNestedObjectKeys(obj[property]))
if (returnedValue == 0) {
return Object.keys(obj[property])[0]
}
returnedValue = Object.keys(obj[property])[0]
if (returnedValue != obj[property[0]]) {
return Object.keys(obj[property])[0]
}
else if (returnedValue == firstLevel) {
return keys
}
}
The function should return the key name and push (unshift) it to string and then return it, but the unshift doesnt do what I expect and in the returnedValue is not a expected returned string.
I approached it the way that the function findd the deepest (empty) object, and starts returning the name of the key. The thing is that I must return the key name AND push it to the string, which I can't find the way to accomplish at once.
Your first solution is pretty close, but has one problem (well, one main problem): when the value is type object, you don't add its key to the array. So how is it supposed to get into the array? Give this a shot:
function convertKeysToString(obj) {
let keys = [];
for (let key in obj) {
keys.push(key.toString());
if (typeof obj[key] === 'object') {
keys = keys.concat(convertKeysToString(obj[key]));
}
}
return keys;
}
Other things you may want to consider:
typeof null is object.
typeof [] is also object.
You could have a look to object, which are truthy and typeof object.
const
getKeys = object => (keys => [
...keys.flatMap(key => object[key] && typeof object[key] === 'object'
? [key, ...getKeys(object[key])]
: [key]
)
])(Object.keys(object)),
data = { OBJECT1: { ATTRIBUTE3: { PARAMETER2: { PROPERTY1: {} } } } },
result = getKeys(data);
console.log(result);

How to check if and object is empty (deep)?

Take this:
var lists:{
item1:{}
,item2:{}
,item3:{}
,item4:{}
}
Since it's substantially empty, I want a function (maybe but not necessarily a _lodash one) that checks it and say that is empty.
Something like
is_empty(lists) // >> true (because every property resolves to an empty object)
How to?
You can iterate over the values of the object and check if all of them are empty:
var lists = {
item1:{},
item2:{},
item3:{},
item4:{}
}
//ES6:
function isEmpty(obj) {
return Object.keys(obj).every(k => !Object.keys(obj[k]).length)
}
console.log(isEmpty(lists));
// ES5
function isEmpty(obj) {
return Object.keys(obj).every(function(k) {
return !Object.keys(obj[k]).length}
)
}
console.log(isEmpty(lists));
If lists is always an object of objects, you can iterate over all values with Object.values and check that each value (inner object) has no keys:
const isEmpty = outer => Object.values(outer).every(
inner => Object.keys(inner).length === 0
);
var lists = {
item1:{}
,item2:{}
,item3:{}
,item4:{}
}
var lists2 = {
item1:{}
,item2:{}
,item3:{}
,item4:{}
,item5:{ foo: 'bar' }
}
console.log(isEmpty(lists));
console.log(isEmpty(lists2));
This solution with check for the emptyness of the eternally nested object.
Note: This will treat empty string '' and boolean false as empty as well. If you need special support for stings then may be you can do some tweaking in the below code.
const isDeeplyEmpty = item => {
if(typeof item === 'boolean') return !item;
else if(typeof item === 'number') return false;
else if(typeof item === 'object') {
return Object.keys(item).every(k => {
if(['object', 'boolean', 'number'].includes(typeof item[k])) {
return isDeeplyEmpty(item[k]);
}
return _.isEmpty(item[k]);
})
}
return !item;
};

Search a deeply nested value in array of objects in javascript

I'm basically trying to implement a search for any given value should look in the array of object key values(there can also be nested objects). Here is an example. The below function will take an object and a query to search in array objects key values. So, if a match is found it should filter from that array.
function searchObj (obj, query) {
for (var key in obj) {
var value = obj[key];
if (typeof value === 'object') {
searchObj(value, query);
}
if (typeof value === 'string' && value.toLowerCase().indexOf(query.toLowerCase()) > -1) {
return obj;
}
}
}
here is the dummy data
var demoData=[
{id:1,desc:{original:'trans1'},date:'2017-07-16'},
{id:2,desc:{original:'trans2'},date:'2017-07-12'},
{id:3,desc:{original:'trans3'},date:'2017-07-11'},
{id:4,desc:{original:'trans4'},date:'2017-07-15'}
];
here is the array I'm filtering object of the match
var searchFilter = demoData.filter(function(obj){
return searchObj(obj, 'trans1');
});
console.log(searchFilter);
for example: if I call searchObj(obj,'2017-07-15') it returns that particular object but if I search for trans1 or simply trans it should look into the object and then return the match. I'm kinda stuck now any help would be appreciated. Thanks.
Case 1 is working because you are not hitting the recursion. But in case 2, you are keep searching even after found the result.
return the object once you find.
if (typeof value === 'object') {
return searchObj(value, query);
}
if (typeof value === 'string' && value.toLowerCase().indexOf(query.toLowerCase()) > -1) {
return obj;
}
function searchObj (obj, query) {
for (var key in obj) {
var value = obj[key];
if (typeof value === 'object') {
return searchObj(value, query);
}
if (typeof value === 'string' && value.toLowerCase().indexOf(query.toLowerCase()) > -1) {
return obj;
}
}
}
var demoData=[
{id:1,desc:{original:'trans1'},date:'2017-07-16'},
{id:2,desc:{original:'trans2'},date:'2017-07-12'},
{id:3,desc:{original:'trans3'},date:'2017-07-11'},
{id:4,desc:{original:'trans4'},date:'2017-07-15'}
];
var searchFilter = demoData.filter(function(obj){
return searchObj(obj, 'trans1');
});
console.log(searchFilter);
Another way to look at this is to just use JSON.stringify and search within that:
searchObj(obj, string) {
const regExpFlags = 'gi',
regExp = new RegExp(string, regExpFlags);
return JSON.stringify(obj).match(regExp);
}
And then test the search pattern:
var searchFilter = demoData.filter(function(obj){
return searchObj(obj, 'trans1');
});
console.log(searchFilter);
You can even go further and implement a loose search by providing an array of strings:
searchObj(obj, string) {
const jsonString = JSON.stringify(obj);
regExpFlags = 'gi',
regExpArray = string.split(' ');
testArray = [];
regExpArray.forEach(term => {
let regExp = new RegExp(term, regExpFlags);
if (jsonString.match(regExp) {
testArray.push(term);
}
});
return regExpArray.length === testArray.length;
}
I modified the data:
var demoData=[
{id:1,desc:{original:'trans1'},date:'2017-07-16'},
{id:1,desc:{original:'trans2'},date:'2017-07-12'},
{id:1,desc:{original:'trans3'},date:'2017-07-13'},
{id:2,desc:{original:'trans4'},date:'2017-07-12'},
{id:3,desc:{original:'trans5'},date:'2017-07-12'},
{id:4,desc:{original:'trans6'},date:'2017-07-15'},
{id:1,desc:{original:'trans7'},date:'2017-07-12'}
];
And the search term:
var searchFilter = demoData.filter(function(obj){
return searchObj(obj, 'trans 2017-07-12');
});
console.log(searchFilter);
One important thing to note here is the performance of JSON.stringify, so this worked fine for me in a case with a limited number of deep nested objects (<1000).
Probably someone with more experience can shed some light on this.

How to iterate a json object if it has combination of string,boolean and number type

I had a node.js app where it takes JSON object and then it encrypts the JSON object key value. I had a function which takes value and then encrypts data. Now I need to iterate only the JSON key value to the function which I'm able to do using.
var JsonData = JSON.parse(jsonString);
var callFunction = iterate(JsonData);
function iterate(JsonData) {
for (var exKey in JsonData) {
if (JsonData.hasOwnProperty(exKey)) {
if (typeof JsonData[exKey] == "object") {
iterate(JsonData[exKey]);
} else {
JsonData[exKey] = encrypt(JsonData[exKey]);
}
}
}
}
var encrpted = JSON.stringify(JsonData);
But the problem is I'm able to iterate only the string type JSON object.i.e., (ex {"name":"sam","gender":"male"}). If we are having JSON object with boolean or number or both type along with string type,it is not able to iterate and I'm getting some error..(ex. {"name":"sam","age":21,"isMarried":false}).
So how can I iterate through that function if I have other than string type? I know that using replace function we can convert boolean, num type to string and then pass to function.But since I'm doing encryption and then decryption, here after decrypted we get everything in string type, which I don't want.They need to be in their original type.So I think this will not work. So can anyone suggest any ideas and help me. Hope my question is clear. Any suggestions appreciated.
If you want to iterate and parse all properties of your JSON object, You could use Object.keys() this way :
obj = {
booleanVar : true,
numericVar : 125,
stringVar : "a string"
};
var iterate = JsonData => Object.keys(JsonData).forEach(key => console.log(JsonData[key]));
iterate(obj); // true
// 125
// a string
Remove your first if condition .
Example :
function iterate(JsonData) {
for (var exKey in JsonData) {
if (typeof JsonData[exKey] == "object") {
iterate(JsonData[exKey]);
} else {
JsonData[exKey] = encrypt(JsonData[exKey]);
}
}
}

Get an object of a dictionary by attribute

I have a dictionary:
[ object , object, object, object, object ]
object contains: id and name.
I have an Id ('123456') and I want to get the object with this id.
Is there another solution how can I do it without for loop on the objects?
any help appreciated!
Hate loops, then go for recursion, i just assumed that you are having that array in a variable called as xArr
var xObj = check(0,"123456");
function check(cnt,id) {
if(xArr[cnt].id === id)
{
return xArr[cnt];
}
else if(cnt === xArr.length - 1) {
return null;
}
else {
cnt += 1;
return check(cnt, id);
}
}
That's an array, you could use jQuery.grep to get the elements with id "123456".
var result = $.grep(arr, function(obj) {
return obj.id === '123456';
});
Array also provide an .filter method (need a polyfill for browsers not support it):
var result = arr.filter(function(obj) {
return obj.id === '123456';
});
If you want to use a vanilla JS method, you can use filter. This pretty much does the same as $.grep.
var result = arr.filter(function (obj) {
return obj.id === '123456';
});

Categories