Two dimensional array in Javascript, [num][value1, value2, value3] - javascript

I'm trying to create a 2D array in JS that I can return from my method. I basically want to do something like this:
var msg[][4] = [][entryID, entryName, entryURL, entryDesc];
for (var i = 0, len = bookmarks.length; i < len; i++) {
var id = bookmarks[i].getElementsByTagName('id')[0].firstChild.nodeValue;
var name = bookmarks[i].getElementsByTagName('name')[0].firstChild.nodeValue;
var url = bookmarks[i].getElementsByTagName('url')[0].firstChild.nodeValue;
var desc = bookmarks[i].getElementsByTagName('desc')[0].firstChild.nodeValue;
msg[i][entryID] = id;
msg[i][entryName] = name;
msg[i][entryURL] = entryURL;
msg[i][entryDesc] = entryDesc;
}
The first line msg[][4] throws an error. I'm not sure if or how I can do something like that. Thanks.

If entryID etc is supposed to be a string, then I think what you actually want is an array of objects:
var msg = [];
for (var i = 0, len = bookmarks.length; i < len; i++) {
msg.push({
entryID: bookmarks[i].getElementsByTagName('id')[0].firstChild.nodeValue,
entryName: bookmarks[i].getElementsByTagName('name')[0].firstChild.nodeValue,
entryURL: bookmarks[i].getElementsByTagName('url')[0].firstChild.nodeValue,
entryDesc: bookmarks[i].getElementsByTagName('desc')[0].firstChild.nodeValue,
});
}
You can then access e.g. the second entry with msg[1].entryID. Instead of creating an object, you can simply create an array as well, but using an object is more descriptive in my opinion.
JavaScript does not have multi-dimensional arrays. What you can create are arrays of arrays (of arrays...) or arrays of objects (of arrays/objects ...). Arrays in JavaScript are dynamic, therefore it is not necessary to initialize them with any size. Just keep adding whatever vaue you want to the array.

Related

Javascript - build array in loop

I'm trying to populate an array from a JSON feed. My code looks something like this:
// multiple arrays
var linje_1 = []
var linje_2 = []
// loop from json feed to populate array
for( var i = 0; i < data.length; i++) {
// I'm trying to "build" the array here. I know for sure that data[i] is good value that match the suffix of the array.
arrayname = 'linje_'+data[i];
arrayname.push({ label: data[i].x_+''+sid[a]+'', y: data[i].y_+''+sid[a]+'' })
}
Does anybody have any suggestions on how to solve the above?
The problem is that the code will not accept arrayname, but if I change and hardcode linje_1, everything works as expected.
When you define a variable arrayname = 'linje_'+data[i]; then its type is String. Strings are not arrays, you can't treat them like array, they don't have array methods.
If you want to dynamically construct the name of the variable, the best thing you can do is to use object and its keys:
var lines = {
linje_1: [],
linje_2: []
};
for (var i = 0; i < data.length; i++) {
var arrayname = 'linje_' + data[i];
lines[arrayname].push({ label: data[i].x_ + sid[a], y: data[i].y_ + sid[a]});
}
Also note, that I cleaned up the code a little (things like data[i].x_ + '' + sid[a] + '').
You're pushing data to a String, not an array. Try this:
window[arrayname].push(/* ... */);
if your variables are declared in the scope of the window, they can be referenced in multiple manners:
myArray
window.myArray
window['myArray'] // You want this one
You're using the same variable for an array and string.
arrayname = 'linje_'+data[i];
arrayname.push({ label: data[i].x_+''+sid[a]+'', y: data[i].y_+''+sid[a]+'' })
The variable arrayname is defined as a string, but then you call the push method which is only a method for arrays.

cannot iterate through array and change value in JS

I have to iterate through an array, change one of its values, and create another array refelecting the changes.
this is what I have so far:
JS:
var arr = new Array();
arr['t1'] = "sdfsdf";
arr['t2'] = "sdfsdf";
arr['t3'] = "sdfsdf";
arr['t4'] = "sdfsdf";
arr['t5'] = "sdfsdf";
var last = new Array();
for (var i = 0; i <= 5; i++) {
arr['t2'] = i;
last.push(arr);
}
console.log(last);
Unfortunately, these are my results
As you can see, I am not getting the results needed as 0,1,2.. instead I am getting 2, 2, 2..
This is what i would like my results to be:
How can I fix this?
You have to make a copy, otherwise you are dealing with reference to the same object all the time. As it was said before - javascript does not have associate arrays, only objects with properties.
var arr = {}; // empty object
arr['t1'] = "sdfsdf";
arr['t2'] = "sdfsdf";
arr['t3'] = "sdfsdf";
arr['t4'] = "sdfsdf";
arr['t5'] = "sdfsdf";
var last = new Array();
for (var i = 0; i <= 5; i++) {
var copy = JSON.parse(JSON.stringify(arr)); //create a copy, one of the ways
copy['t2'] = i; // set value of its element
last.push(copy); // push copy into last
}
console.log(last);
ps: you can use dot notation arr.t1 instead of arr['t1']
The array access with ['t2'] is not the problem. This is a regular JavaScript feature.
The problem is: You are adding the SAME array to "last" (5 times in code, 3 times in the screenshot).
Every time you set ['t2'] = i, you will change the values in "last" also, because they are actually just references to the same array-instance.
You must create a copy/clone of the array before you add it to "last".
This is what will happen in all languages where arrays are references to objects (Java, C#...). It would work with C++ STL though.

Sorting 2D javascript array

I have an array containing a list of tags and count.
tags_array[0] = tags;
tags_array[1] = tags_count;
I need to sort the arrays base on the count so that I can pick out the top few tags.
Sort one, while storing the sort comparisons. Then sort the other using those results:
var res = [];
tags_count.sort( function( a, b ){ return res.push( a=a-b ), a; } );
tags.sort( function(){ return res.shift(); } );
Supposing tags and tags_count are 2 arrays of same length, I would first build a proper array of objects :
var array = [];
for (var i=0; i<tags_count.length; i++) {
array.push({tag:tags[i], count:tags_count[i]});
}
And then sort on the count :
array.sort(function(a, b) {return a.count-b.count});
If you need to get your arrays back after that, you may do
for (var i=0; i<array.length; i++) {
tags[i] = array[i].tag;
tags_count[i] = array[i].count;
}
Demonstration
Assuming that both tags and tags_count are arrays with the same length (that part of the question wasn't too clear), the following is one way to do the trick.
var tags_array = new Array();
for (var i = 0; i < tags.length; i++)
{
tags_array[i] = {};
tags_array[i].tagName = tags[i];
tags_array[i].tagCount = tags_count[i];
}
tags_array.sort(function(a,b){return b.tagCount-a.tagCount});
One should note that it might be possible to structure the data in this way from the start instead of rewriting it like this, in which case that is preferable. Likewise, a better structure can be used to save the data, but this will work.

Can't instantiate an array of objects

I'm trying to load up an array of objects that is an array itself, so to speak. So I have an array of names(members) then I'm making a master list that will have name, bugs, enhance, etc. in one row for every name. So I run a simple for loop to load master list but it is telling me that for (0) i, masterList[i].name cannot be loaded because it is undefined. Is there a way around this? Thanks
var mem = getMembers();//get a array of members
var memlen = mem.length;
var masterList = [memlen]; //set to number of members
for(i=0; i < memlen; i++){
masterList[i].name = mem[i]; //set .name to the members list name at i
masterList[i].bugs = 0;
masterList[i].enhance = 0;
masterList[i].epic = 0;
masterList[i].dev = 0;
masterList[i].high = 0;
}
To create your array with a predefined size, use this :
masterList = new Array(memlen);
(with masterList = [memlen] you were just creating an array whose first item is memlen. This wasn't so problematic because the array was automatically growing in the loop but that wasn't your intent)
After that, you need to create each masterList[i] :
var masterList = new Array(memlen);
for (var i=0; i < memlen; i++){
masterList[i] = {};
masterList[i].name = mem[i]; //set .name to the members list name at i
If you don't do it, it's undefined, hence the error you have.
I also added var in the loop declaration to avoid the accidental erasing of another variable named i.
A correct version would be:
var mem = getMembers();//get a array of members
var memlen = mem.length;
var masterList = []; //set to number of members
for(var i=0; i < memlen; i++){
masterList[i] = {
name: mem[i], //set .name to the members list name at i
bugs: 0,
enhance: 0,
epic: 0,
dev: 0,
high: 0
};
}
var x = [7]; does not create a 7-element array. it creates a single element array, index 0, with value 7. You need to do var x = array(7) instead, plus initialize each of those elements to be an object instead, within your loop.
This doesn't set a length. It just creates a new Array with a single member set to the length.
var masterList = [memlen]; //set to number of members
Since you seem to already have an Array, you can use .map to build a new one.
var mem = getMembers();
var masterList = mem.map(function(item) {
return {
name: item.name, bugs: 0, enhance: 0, epic: 0, dev: 0, high: 0
};
});

A good way to associate a counter to each member of an array in Javascript?

I have an array of strings in Javascript like `var elements = ["string1", "string2"]; The array is created dynamically so it could contain any number of strings. I want to associate a counter to each element of the array. The counter will increment or decrement during the webpage's life.
I was going to try element["string1"].counter = 1; but it didn't work.
What's a good way to implement this?
If you had an array var elements = ["string1", "string2"], you could not access an element with elements["string1"], you are using the value not the index. elements[0] is the correct form of access to the element, using the numerical key.
Even then, strings are special types of object and do not appear to take additional parameters readily, at least not when I tested a moment ago. Which is odd.
You could quickly knock the array in to a set of objects with separate text and counter components.
var elements = ["string1", "string2"];
var elementsWithCounter = [];
for(var index = 0; index < elements.length; index++) {
elementsWithCounter[i] = { text: elements[index], counter: 1 };
}
You could also create a "hash table" using a plain object such as:
var counter = {};
for(var i = elements.length; i--; ) {
counter[elements[i]] = 1;
}
Then you could increment the counter with:
counter['string1'] += 1;
or
counter[elements[0]] += 1;
This might help you.
elementArray = ["string1", "string2"]
function setCounter(str, val) {
for (var i = 0; i < elementArray.length; i++) {
if (str === elementArray[i]) elementArray[i].counter = val;
}
}
function getCounter(str) {
for (var i = 0; i < elementArray.length; i++) {
if (str === elementArray[i]) return elementArray[i].counter;
}
}
setCounter("string1", 5);
getCounter("string1");
Alternatively just access elementArray[index].counter
Javascript primitives/built in objects can't have properties/attributes added to their prototype (i.e. String.prototype.counter = -1 doesn't work correctly). Image, String, Date, Array all can't have properties added.
Maybe instead of a string you should make it an object, similar to what Orbling has posted.

Categories