I have the below code:
var changes = new Array();
$(".item_prices").on("blur", function(){
var item_id = $(this).attr("id");
var item_price = $(this).html();
changes[item_id] = item_price;
});
Every time a new value is entered, I want to save the item's ID as the key and its price as the value. If I save items with IDs 4 and 6 and prices 1.99 and 2.99, respectively, I get the following array:
{,,,,1.99,,2.99}
How do I add to the array without incurring empty values?
Use object, not Array:
var changes = {};
The rest is the same.
Key-value should always be saved in an object.
Since you're using jQuery, here is another answer to an unasked question,
Use native javascript functions when it's possible and simple, specially when it's even simpler:
var item_id = $(this).attr("id");
var item_price = $(this).html();
Can and should be:
var item_id = this.id
var item_price = this.innerHTML;
You don't want an array, a simple object will form a collection of key value pairs for you:
var changes = {};
If / when the time comes to enumerate these changes:
for (var name in changes) {
if (changes.hasOwnProperty(name)) {
var value = changes[name];
...
}
}
Arrays are a special case of objects, whose elements have consecutive integer keys. You don't have consecutive keys, so Array is "filling the gaps" for you.
Use a barebones Object instead:
var changes = {};
Related
If i try to add more keys with values to a javascript object it alters the value of all keys, not just the one I have added.
var corridorObject = {};
var makeObjects = [];
function someFunction(){
var a = makePoints;
var Corridor = viewer.entities.add({
corridor : {
positions : (a),
width : 10.0,
material : Cesium.Color.GREEN,
}
var idv0 = Corridor.id
corridorObject[idv0] = makeObjects;
console.log(corridorObject);
makeObjects.length=0;
}
The Corridor ID is a guid, the makeObjects an array of objects, when I run this it adds the key perfectly, and the values, but when I run it a second time it adds a new key with the new ID and new values, but it also changes the values for all the other keys to the most recent values.
here is the console, as you can see the first time the array for the ID is 3 long the second time with the same id its 2 long
Object {91ff9967-7019-4e76-846e-c0e125481060: Array[3]}
Object {91ff9967-7019-4e76-846e-c0e125481060: Array[2], 3de2c2b1-5fb6-495c-9034-2b37713e5c30: Array[2]}
Sorry to be more clear, this is from Cesiumjs, its taking points and converting them to a corridor, the corridor id and an array of the points that made it are then added to this object. The array of points is then emptied.
If you are repeating
var corridorObject = {};
var makeObjects = [];
var idv0 = Corridor.id
corridorObject[idv0] = makeObjects;
console.log(corridorObject);
These line of code then It will initialise
var corridorObject = {};
Thats why you will get only one key. Put initialization outside of the iteration
Very close but slightly more complex than this question I have an array and I want to obtain the index of the array of the first occurrence of a value of a given object of this array.
My array has several objects of integer and text, and has an id object of integers (which I call with this instruction wup[i].id).
[edit] The array comes from reading a csv file with header with papaparse.
wup = ["id", "cityName", etc ... ]
[20002, "Tokyo", etc ... ]
[20003, "Goiânia", etc ... ]
It is in this id object only that I want to find the input value and finally get the index of this input value. This is certainly using indexOf but how to focus the search only in the id object?
[edit] the instruction that fails is the following (try to find the occurrence of tn[iter].idOri in the array wup, that I expect to retrieve in the variable iOri):
var iOri = wup.indexOf(tn[iter].idOri);
Hoping it is clear enough.
There are lots of ways to do this, map your array down to a flat array of ids:
var myId = 3;
var ids = array.map(function(obj) {
return obj.id;
});
var index = ids.indexOf(myId);
A more succinct (and better - because it only requires one iteration) method would be to use Array.findIndex:
var myId = 3;
var index = array.findIndex(function(obj) {
return obj.id === myId;
});
With es6:
var myId = 3;
var index = array.map(obj => obj.id).indexOf(myId);
or
var myId = 3;
var index = array.findIndex(obj => obj.id === myId);
I currently the following jQuery collection / object:
[li.row-0, li.row-1, li.row-2, li-row-2, li.row-2, li.row-3]
Each class name is dynamically added to each element by a previous method. The only consistent part of the class name is row-. The number can be anywhere from 0 - ∞.
I want to create a new array or object of elements that are grouped by same dynamic class name:
[li.row-0]
[li.row-1]
[li.row-2, li.row-2, li.row-2, li.row-2]
[li.row-3]
The above is just a guess of the outcome, as I am not 100% sure how best to achieve this.
The aim is to be able to loop through .row-0, .row-1, .row-2, .row-3 and do something with the elements in each individual row.
I would do this :
var map = [].reduce.call(arr, function(map, v){
(map[v.className]||(map[v.className]=[])).push(v);
return map;
}, {});
var arr2 = [];
for (var className in map) arr2.push(map[className]);
The reduce builds a map having as keys the class names and with values the arrays of the elements having that class name.
I use [].reduce.call(arr, instead of arr.reduce( so that it works for standard arrays, jQuery collections, nodelists, etc.
Then the loop builds an array from that map. You might find the map more useful than the final array.
This shows you a general way of achieving this, though you're probably using elements rather than strings, but hopefully this will help
var tst = ['li.row-0','li.row-1','li.row-2','li.row-2','li.row-2','li.row-3'];
var grouped = [];
for(var i in tst)
{
var text = tst[i];
var num = text.replace('li.row-','');
if(!grouped[num]) grouped[num] = [];
grouped[num].push(text);
}
console.log(grouped);//[["li.row-0"], ["li.row-1"], ["li.row-2", "li.row-2", "li.row-2"], ["li.row-3"]]
Using elements:
var tst = [li.row-0,li.row-1,li.row-2,li.row-2,li.row-2,li.row-3];
var grouped = [];
for(var i in tst)
{
var text = tst[i].className;
var num = text.replace('row-','');
if(!grouped[num]) grouped[num] = [];
grouped[num].push(text);
}
console.log(grouped);//[["li.row-0"], ["li.row-1"], ["li.row-2", "li.row-2", "li.row-2"], ["li.row-3"]]
This method is more verbose and allows more complex grouping if need be (if other attributes come into play)
I would do something like the following:
var arr = ['li.row-0', 'li.row-1', 'li.row-2', 'li.row-2', 'li.row-2', 'li.row-3'];
var result = {};
$.each(arr, function (index, item) {
var ind = item.toString().split('row-')[1];
(result[ind] || (result[ind] = [])).push(item);
});
console.log(result);
i am trying to pass non numeric index values through JSON but am not getting the data.
var ConditionArray = new Array();
ConditionArray[0] = "1";
ConditionArray[1] = "2";
ConditionArray[2] = "3";
ConditionArray['module'] = "Test";
ConditionArray['table'] = "tab_test";
var Data = JSON.stringify(ConditionArray);
When i alert the Data Variable it has the Values 1,2 and 3 but module and table are not included. How can this be added so that the whole string is passed.
EDIT : And what if i have some multidimensional elements also included like
ConditionArray[0] = new Array();
ConditionArray[0] = "11";
JSON structure only recognizes numeric properties of an Array. Anything else is ignored.
You need an Object structure if you want to mix them.
var ConditionArray = new Object();
This would be an better approach:
var values = {
array : ["1", "2", "3"],
module : "Test",
table : "tab_test"
};
var data = JSON.stringify(values);
Since javascript array accepts numeric index only. If you want non numeric index,use Object instead.
var ConditionArray = {};
ConditionArray[0] = "1";
ConditionArray[1] = "2";
ConditionArray[2] = "3";
ConditionArray['module'] = "Test";
ConditionArray['table'] = "tab_test";
var Data = JSON.stringify(ConditionArray);
Here is the working DEMO : http://jsfiddle.net/cUhha/
According to the algorithm for JSON.stringfy (step 4b), only the (numeric) indices of arrays are stringified.
This is because Array does not contain your elements.
When you do this:
ConditionArray['module'] = "Test";
You actually add a property to the ConditionArray, not elements. While JSON.stringify converts to string only elements of the ConditionArray. For example:
var arr = new Array;
arr['str'] = 'string';
console.log(arr.length) //outputs 0
You need to use an Object instead of Array
If you change the first line to
var ConditionArray = new Object();
you will achieve the desired outcome.
If for some reason you cannot convert your array into object, for instance you are working on a big framework or legacy code that you dont want to touch and your job is only to add som feature which requires JSON API use, you should consider using JSON.stringify(json,function(k,v){}) version of the API.
In the function you can now decide what to do with value of key is of a specific type.
this is the way how I solved this problem
Where tblItemsTypeform is array and arrange is de index of the array
:
let itemsData = [];
for(var i = 0; i <= this.tblItemsTypeform.length -1;i++){
let itemsForms = {
arrange: i,
values: this.tblItemsTypeform[i]
}
itemsData.push(itemsForms)
}
And finally use this in a variable to send to api:
var data = JSON.stringify(itemsData)
var cur_storage_unit = $('#storage_unit').val();
$('.size_unit').change(function() {
var id = $(this).attr('id');
//This is how I want it to work, but not sure how
'cur_' + id = $(this).val();
});
The user 'changes' a of class 'size_unit' and id of 'storage_unit'. I want to then set the value of 'cur_storage_unit' to the new value of 'storage_unit'. In italics is how I want it to work, but I'm not sure the syntax of how to get it to work. Thanks!
You're probably better off using an Object, and storing it in there.
var cur_storage_unit = $('#storage_unit').val();
var values = {}; // storage for multiple values
$('.size_unit').change(function() {
var id = this.id;
values['cur_' + id] = this.value; // store this value in the "values" object
});
// Accessible via values object
alert( values["cur_theid"] );
you can create a new property on an object using a string as a key
var myObj = {};
myObj['cur_'+id] = $(this).val();
so in your case you would want an object with a known name where you can add dynamically named properties.
If it's global you can do window['cur_'+id];