Search Json Array - javascript

I got a json array like below:
[
{"value":"uk-icon-adjust","title":"Adjust","url":"#", "text":""},
{"value":"uk-icon-adn","title":"Adn","url":"#", "text":""},
{"value":"uk-icon-align-center","title":"Align center","url":"#", "text":""},
{"value":"uk-icon-align-justify","title":"Align justify","url":"#", "text":""},
{"value":"uk-icon-align-left","title":"Align left","url":"#", "text":""}
]
I want to search this json array for specific titles. But the problem is, that I want to search with a Regex.
e.g: sb searchs for "ad" -> the function should return the first two json strings (Adjust and Adn).
I have no idea, now to setup a javascript function which can achieve this.
Some ideas?

Try this:
var array = [
{"value":"uk-icon-adjust","title":"Adjust","url":"#", "text":""},
{"value":"uk-icon-adn","title":"Adn","url":"#", "text":""},
{"value":"uk-icon-align-center","title":"Align center","url":"#", "text":""},
{"value":"uk-icon-align-justify","title":"Align justify","url":"#", "text":""},
{"value":"uk-icon-align-left","title":"Align left","url":"#", "text":""}
],
searchString = 'ad',
searchRegExp = new RegExp(searchString , 'i'); // 'i' makes the RegExp ignore case
var result = array.filter(function(e){ // Filter out any items that don't pass the
return searchRegExp.test(e.title); // RegExp test.
});
Result:
[
{"value":"uk-icon-adjust","title":"Adjust","url":"#","text":""},
{"value":"uk-icon-adn","title":"Adn","url":"#","text":""}
]
If you only want an array of titles, you can then map the result, like this:
var titles = result.map(function(e){
return e.title;
});
Titles:
["Adjust", "Adn"]
You'll want to do this mapping after filtering the array, for efficiency. This way you'll only have to iterate over the filtered result, instead of first iterating over all items to get the titles, then iterating over all of them again to filter them.
Of course, this can be combined with the filtering:
var result = array.filter(function(e){
return searchRegExp.test(e.title);
}).map(function(e){
return e.title;
});
Please keep in mind that both Array.prototype.filter() as Array.prototype.map() Aren't supported in IE 8 or lower. However, the pages I linked to do have some polyfills to make these functions work in older versions of IE.

That's an native Object. You can do it this way though, by first creating an Array of titles by using Array.map and then filter them using Array.filter
var titles = obj.filter(function(o){
return /^ad/i.test(o.title);
}).map(function(o){ return o.title; });

Amit Joki answer is the answer.
If you don't want to use map(), you could also try:
var json = [
{"value":"uk-icon-adjust","title":"Adjust","url":"#", "text":""},
{"value":"uk-icon-adn","title":"Adn","url":"#", "text":""},
{"value":"uk-icon-align-center","title":"Align center","url":"#", "text":""},
{"value":"uk-icon-align-justify","title":"Align justify","url":"#", "text":""},
{"value":"uk-icon-align-left","title":"Align left","url":"#", "text":""}
];
function search(array, re) {
var regexp = new RegExp(re, 'gi');
for (var i = 0; i < array.length; i++) {
return array[i].title.match(regexp);
}
throw "Couldn't find object like " + re;
}
console.info(search(json, 'ad'));

Related

Concatenate elements of an array Javascript

I have a list of hrefs with product data:name and it's id. First of all i removed prod Id that i'll use as separate variable.
After this, the remained part of href should be used as the product name.
var prodHref = document.querySelectorAll('.widget-products-list-item-label');
var allHref = [];
for(var i=0;i<prodHref.length;i++){
allHref.push(prodHref[i].href.split('/')[5])
}
var prodName = [];
for(var i=0;i<allHref .length;i++){
prodName.push(allHref [i].slice(0, -1))
}
var prodNameNew=[];
for(var i=0;i<prodName .length;i++){
prodNameNew.push(prodName[i].slice(0, -1))
}
So, the final result is on the attached screen. N
How i have concatenate all the elements of each array in order to get new arrays in the following format: Nokia G20 4 64 Albastru, Motorola G60 gri etc
Thank You
You want to capitalize the items of the inner arrays and then join them by space.
One way to do it is:
let result = arr.map(a => a.map(capitalize))
.map(a => a.join(" "))
where capitalize should be a function that takes a string and returns a string with first letter in upper case if possible.
You can find this in answers for the more specific SO question:
How do I make the first letter of a string uppercase in JavaScript?
Instead of 3 separate loops, we can get the substring based on single iteration only using Array.map() along with String.slice().
const prodHref = [{
href: "https://abc/def/ghi/alpha/mno"
}, {
href: "https://abc1/def1/ghi1/beta/mno1"
}, {
href: "https://abc2/def2/ghi2/gamma/mno2"
}, {
href: "https://abc3/def3/ghi3/omicron/mno3"
}];
const allHref = prodHref.map((obj) => obj.href.split('/')[5].slice(0, -2));
console.log(allHref);
Now you can use Array.join() method to join the result array.
const allHref = ["alp", "be", "gam", "omicr"];
console.log(allHref.join(" "));

converting each array value ias object in javascript not working

This is my array:
var country = ["US(+1)","IND(+91)"];
And i want to convert my array in this below format:
country = [
{
title: "US(+1)",
},
{
title: "IND(+91)",
}
]
word title should be same for each array value.
with this code am trying to get my expected result as above
var obj = country.reduce(function(o, val) { o['title'][] = val; return o; }, {});
But my output is comes like this as below: only last index is taking place
{"title":"IND(+91)"} this is wrong output which i dont want
You may be able to do it with reduce but it's much easier to use map:
var country = ["US(+1)","IND(+91)"];
var obj = country.map(function(c){return {title:c}});
console.log("country:", country);
console.log("obj:", obj);
map is for when you want to turn an array of things into another array of things, and reduce is when you want to turn an array of things into just a single thing.
var country = ["US(+1)","IND(+91)"];
I would use a more descriptive word since it is a list of countries.
var countries = ["US(+1)","IND(+91)"];
But to answer your question, to manipulate an array into a new array, I like to use the array.map method:
var objects = countries.map(function(country){ return { title: country } });
Here is the documentation for map:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map?v=control

Split an object into array of objects based on a condition in JavaScript

How to split an object into array of objects based on a condition.
oldObject = {"Chicago, IL:Myrtle Beach, SC": 0.005340186908091907,
"Portsmouth, NH:Rock Hill, SC": 0.0063224791225441205,
"Columbia, SC:Laconia, NH": 0.006360767389277389,
"Council Bluffs, IA:Derry, NH": 0.0016636141225441225}
Above is the given sample object. I want to make an array of objects like this,
newArray = [{"city":"Chicago", "similarTo":"Myrtle"},
{"city":"Portsmouth", "similarTo":"Rock Hill"},
{"city":"Columbia", "similarTo":"Laconia"},
{"city":"Council Bluffs", "similarTo":"Derry"}]
I have been scratching my head with this for a while now. How can I get the above array(newArray)?
Here is a bunch of code you can try.
1) Iterate over oldObject and get the name of the property.
2) Split that name into an array based on the ":" character, since it separates the cities
3) Go over that new array, splitting it on the "," character (so as not to get the states).
4) Put the values into the newObject, based on whether it's the first or second part of the original property name.
5) Push that newObject, now with items, into a newArray.
Basically, this parses apart the name and does some array splitting to get at the right values. Hope it helps and helps you understand too.
var oldObject = {"Chicago, IL:Myrtle Beach, SC": 0.005340186908091907,
"Portsmouth, NH:Rock Hill, SC": 0.0063224791225441205,
"Columbia, SC:Laconia, NH": 0.006360767389277389,
"Council Bluffs, IA:Derry, NH": 0.0016636141225441225};
var newArray = [];
for (object in oldObject) {
var thisObjectName = object;
var thisObjectAsArray = thisObjectName.split(':');
var newObject = {
'city': '',
'similar_to': ''
};
thisObjectAsArray.forEach(function(element,index,array) {
var thisObjectNameAsArray = element.split(',');
var thisObjectNameCity = thisObjectNameAsArray[0];
if(index===0) {
newObject.city = thisObjectNameCity;
} else if(index===1) {
newObject.similar_to = thisObjectNameCity;
}
});
newArray.push(newObject);
}
console.log(newArray);
PS: to test, run the above code and check your Developer Tools console to see the new array output.

Javascript Array of Objects and Unique Values

I have an array of objects that looks like this:
[
{"name":"Andrea","from":"USA","Food":"Candy"},
{"name":"Matt","from":"Taiwan","Food":"Chicken"},
{"name":"Roddy","from":"USA","Food":"Rice"},
{"name":"Andy","from":"Great Britain","Food":"Steak"},
];
Is there a way to get the list of all countries from the array above, and get rid of the repeated ones?
So from the list above, the list I am to obtain is:
["USA", "Taiwan", "Great Britain"]
Thank you!
Just loop over people and insert unique countries in a new array. Here is an example.
var countries = [];
var people = [
{"name":"Andrea","from":"USA","Food":"Candy"},
{"name":"Matt","from":"Taiwan","Food":"Chicken"},
{"name":"Roddy","from":"USA","Food":"Rice"},
{"name":"Andy","from":"Great Britain","Food":"Steak"},
];
for (var i = 0, l=people.length; i < l; i++) {
if(people[i] && people[i].from) {//ensure country exists
if (countries.indexOf(people[i].from) == -1) {//ensure unique
countries.push(people[i].from);
}
}
}
Yet another variant with reduce
var arr = [
{"name":"Andrea","from":"USA","Food":"Candy"},
{"name":"Matt","from":"Taiwan","Food":"Chicken"},
{"name":"Roddy","from":"USA","Food":"Rice"},
{"name":"Andy","from":"Great Britain","Food":"Steak"},
];
var countries = arr.reduce(function(acc, cur){
if(!acc.map[cur.from]){
acc.map[cur.from]=true;
acc.result.push(cur.from);
}
return acc;
}, {result:[], map:{}}).result;
var arr = [
{"name":"Andrea","from":"USA","Food":"Candy"},
{"name":"Matt","from":"Taiwan","Food":"Chicken"},
{"name":"Roddy","from":"USA","Food":"Rice"},
{"name":"Andy","from":"Great Britain","Food":"Steak"},
];
var countries = arr.reduce(function(acc, cur){
if(!acc.map[cur.from]){
acc.map[cur.from]=true;
acc.result.push(cur.from);
}
return acc;
}, {result:[], map:{}}).result;
document.getElementById('countries').innerHTML = countries.join();
<span id="countries"></span>
If you are already using the excellent Lodash library, the following will do it for you neatly in one line:
var uniqueCountries = _(dataArray).pluck('from').unique().value();
UnderscoreJS has similar functionality using chaining.
For D3.js, the following will do it:
var uniqueCountries = d3.set(dataArray.map(function (x) { return x.from; })).values();
Without doing the unique-ifying on the server and returning that data separately, there is no way to get around looping through all records at least once to do this. For 1000 records or so, though, this will still be very fast.
For plain JS, see other answers.
I'd loop over the Array and put the country into an array if it is not yet inside that array.

What's the best way to query an array in javascript to get just the items from it I want?

I have an array like this (with just over 3000 objects instead of the 3 here):
items = [{name:'charlie', age:'16'}, {name:'ben', age:'18'}, {name:'steve', age:'18'}]
What's the best way to return an array with just the objects of people who are 18? So I want:
items = [{name:'ben', age:'18'}, {name:'steve', age:'18'}]
The best I can think of is this (using jQuery):
newArray = []
$.each(items, function(index, item) {
if(item.age=='18') {
newArray.push(item)
}
})
Considering that there's 3000 thousand objects, and also that I'll be doing that comparison up to fifty times in one go, that's a lot of looping. Is there a better way?
You can use pure javascript
var wanted = items.filter( function(item){return (item.age==18);} );
And if your browser does not support the 1.6 version of javascript you can find an implementation of the filter method at https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/filter
Update
Speedwise there is a huge varying (had an error in the test) difference from a normal loop (depending on browser).. Have a look at this little test i made at http://jsperf.com/array-filter-vs-loop/3
Get matched item and items using find() and filter() method
If you want first matched single item, use find() method which returns single object.
If you want all matched , use filter() method which returns array of objects.
let items = [{name:'charlie', age:'16'},
{name:'ben', age:'18'},
{name:'steve', age:'18'}]
let all = items.filter(item=> item.age==='18')
console.log(all);
let single = items.find(item=> item.age==='18')
console.log(single);
If you're going to do the search often it may be best to keep a version of your data in a form that is quick to access.
I've used underscore.js (http://documentcloud.github.com/underscore/) to make it easy for myself, but this code here will create an object that holds your data indexed by the age field.
You end up with something that looks like this:
{
"16": [
{
"name": "charlie",
"age": "16"
}
],
"18": [
{
"name": "ben",
"age": "18"
},
{
"name": "steve",
"age": "18"
}
]
}
The code:
var itemsByAge = _(items).reduce(function(memo, item) {
memo[item.age] = memo[item.age] || [];
memo[item.age].push(item);
return memo;
}, {});
alert(JSON.stringify(itemsByAge["18"]));
No matter which method you choose (items.filter or any "query language" for json), a for loop is inevitable.
If performance is a concern, I would recommend you to use pure javascript instead of libraries like jQuery which will add overheads to the whole processing as is evident here.
Thus, your code would look like:
var newArray = [];
for(var i=0;i<items.length;i++) {
var item = items[i];
if(item.age == '18') {
newArray.push(item);
}
});
making use of javascript magnificent function eval() which evaluates string as code at runtime, we can define a prototype method for Array type
Array.prototype.where = function (query) {
var newArray = [];
for(var i=0; i<this.length; i++) {
var item = this[i];
if(eval( "item" + query )) {
newArray.push(item);
}
}
return newArray;
};
and use it with any array, passing the query as string
var newArray= items.where('.age >= 18');
Use the filter method of the array, it calls the provided callbackfunction once for each element in an array.
array.filter(<callbackfucntion>[, <Object to use>])
once i had such problem and i solved it like this
1- create an array of array
2- each index create an Index record
e.g.
var pAry=[];
var cAry=[{name:'ben', age:'18'}, {name:'steve', age:'18'}]
pAry[17]=cAry;
This way when u require person with age 18, you will get on index 17.

Categories