For loop to convert series of variables - javascript

I'm trying to create a for loop that does the exact same thing as this code (quests is an array):
Quest0.text = quests[0]
Quest1.text = quests[1]
Quest2.text = quests[2]
Quest3.text = quests[3]
Quest4.text = quests[4]
Quest5.text = quests[5]
Quest6.text = quests[6]
Quest7.text = quests[7]
Quest8.text = quests[8]
Quest9.text = quests[9]
Quest10.text = quests[10]
Quest11.text = quests[11]
Quest12.text = quests[12]
Quest13.text = quests[13]
Quest14.text = quests[14]
Quest15.text = quests[15]
So far all I've got is this (activeQuests is the length of the array quests):
var q = 0;
for (q=0; q <= activeQuests; q++) {
Quest0.text = quests[q]
}
But I don't know how to get it to do the rest.

You could use eval but you probably shouldn't. You should probably rethink your approach if you have such obviously array-like data that you are manipulating manually element by element.
Check out this blog post from Marco van Hylckama Vlieg: "Variable Variables in Javascript". Relevant snippet:
...using the fact that all global variables are held in the window
array.
var i=1;
window['name' + i] = 'Marco';
document.write('got ' + name1);
There we go! Nice, clean and no eval() necessary."

We'd need to know more to give you exact code, but in order to address a variable by string, it needs to be a property of an object. For example
window.example = 'hello world';
alert(window['example']);
So it really depends on what your QuestN variables are. Are they id's of <input> elements? Are they global variables? Are they defined in local scope with the var keyword?

If you can change how Quest.. are defined then define them as an array so you can do:
Quest[q].text = quests[q];
if you can't then temporarily create an array of Quest.. objects:
var QUESTS = [];
QUESTS[0] = Quest0;
QUESTS[1] = Quest1;
QUESTS[2] = Quest2;
QUESTS[3] = Quest3;
QUESTS[4] = Quest4;
QUESTS[5] = Quest5;
QUESTS[6] = Quest6;
QUESTS[7] = Quest7;
QUESTS[8] = Quest8;
QUESTS[9] = Quest9;
QUESTS[10] = Quest10;
QUESTS[11] = Quest11;
QUESTS[12] = Quest12;
QUESTS[13] = Quest13;
QUESTS[14] = Quest14;
QUESTS[15] = Quest15;
Then you can do:
for (var q=0; q<=activeQuests; q++) {
QUESTS[q].text = quests[q]
}
Obviously this is an uglier solution but much better than eval IMHO.

I think you are better off keeping the "quests" array than defining a different variable to each index.
However if you want to loop try eval("Quest" + q + ".text = quests[q]") in the loop.

Related

How do I create a dictionary out of each user with their current game? Discord.js

I thought of somethinh like this:
var userGames = {};
for (i=0; i< client.getListOfOnlineUsers(); i++) {
var key = client.getListOfOnlineUsers()[i];
userGames.key = client.getListOfOnlineUsers()[i].presence.game;
}
Is this the right way to go?
I haven't used discordjs, so correct me if I got anything wrong. As I understand it, getListOfOnlineUsers returns the array of users and user.presence.game will give you the game. If so, you have the correct idea, just a minor correction on line 4:
var userGames = {};
for (i=0; i< client.getListOfOnlineUsers(); i++) {
var key = client.getListOfOnlineUsers()[i];
userGames[key] = client.getListOfOnlineUsers()[i].presence.game;
}
This should work for you. The [key] is used here because key is a variable and the real value of the dictionary key is computed at run-time.
Also, you should probably avoid calling the same function over and over when it returns the same result. Save the data in a variable. Maybe, use forEach and let too.
let userGames = {};
const userList = client.getListOfOnlineUsers();
userList.forEach(u => userGames[u] = u.presence.game);
Looks a lot cleaner imo.

Using a variable increment to create new variables in Javascript

It might be a beginner's question, but I can't seem to find an answer on this.
The data it is getting is data out of a JSon file. I want it to loop through all the rows it is seeing. The loop works how it is written below and returns me the info I need with the rest of the code. I am trying to create multiple variables like testVar1, testVar2, testVar3, .... I don't know if it is possible to do it this way, or if I need to find another solution.
var i = 0;
for (var x in data) {
var testVar1 = data[0][1]; // works
var testVar[i] = data[0][1]; // doesn't
i += 1;
}
How can I make the testVar[i] work ?
What is the correct syntax for this?
Your code misses the initialization of your array variable: var testVar = [];.
⋅
⋅
⋅
Anyway, you may want to create those variables in the window object :
for (var i = 0; i <= 2; i++) {
name = 'var' + i;
window[name] = "value: " + i;
}
console.log(var0);
console.log(var1);
console.log(var2);
That way you can keep using the "short" variable name.
You can wrap all those variables in an object.
instead of:
var testVar1 = data[0][1];
Try:
var Wrapper = {};
//inside the for loop:
Wrapper["testVar" + i] = data[0][i];
...and so on.
You'd access them as Wrapper.testVar1 or Wrapper["testVar" + 1].
The problem you're having is pretty simple. You try to declare a variable as an array and in the same statement try to assign assign a value to a certain index. The reason this doesn't work is because the array needs to be defined explicitly first.
var testVar[i] = data[0][1];
Should be replaced with:
var testVar = []; // outside the loop
testVar[i] = data[0][1]; // inside the loop
Resulting in:
var i = 0,
testVar = [],
data = [
['foo', 'bar', 'baz'],
['kaas', 'is', 'baas']
];
for (var x in data) {
var testVar1 = data[0][1];
testVar[i] = data[0][1];
i += 1;
}
console.log('testVar1', testVar1);
console.log('testVar', testVar);
console.log('testVar[0]', testVar[0]);
console.log('testVar[1]', testVar[1]);
If i isn't an integer you should use an object instead. This can be seen in the answer of Tilepaper, although I advise against the use variables starting with a capital letter since they suggest a constant or a class.

Add items to a Javascript object

My app is hitting a WebAPI that returns some JSON records. I get them via jQuery AJAX and assign the JSON to a JavaScript variable. I can loop through and make changes to existing items without issue. However, how do I add more "records" to this object? I'm trying to understand the structure of the resulting variable.
Here is what I have as a test. Is this the best way?
var trustAccounts = {"accounts":[
{"entityId":12345,
"type":"IOLTA",
"nameOnAccount":"Sam Smith Trust",
"accountNumber":"987654",
"bankCode":"003",
"bankName":"Bank of Stuff",
"accountDate":"12/15/2014",
"status":"A",
"exempt":"N",
"accountId":142922,
"action":"U"}]};
var newaccount = {};
newaccount.entityId = 23456;
newaccount.type = "IOLTA";
newaccount.nameOnAccount = "John Smith Trust";
newaccount.accountNumber = "789456";
newaccount.bankCode = "003";
newaccount.bankName = "Bank of Stuff";
newaccount.accountDate = "12/15/2014";
newaccount.status = "A";
newaccount.exempt = "N";
newaccount.accountId = 142923;
newaccount.action = "U";
trustAccounts.accounts.push(newaccount);
console.log(trustAccounts);
So if we name the returned variable object we can simply create new elements using object.newItemName. Eg below:
object.newItemName = 'Hello World'
You just add them, as if they already existed. A JSON-parsed object is just a normal JavaScript object.
let obj = {};
obj.newProp = 5;
console.log(obj.newProp); // 5
obj['newProp'] = 4;
console.log(obj.newProp); // 4
You can set them in two ways, with the dot-notation or with square brackets ([]). The dot-notation way, the value after the dot is what it's called. The square bracket can accept a string or variable, so you can use it to set a property to a specific name.
If you need to nest things, you have to create each level. For example, if you wanted to set obj.something.aValue, you could do something like this:
let obj = {};
obj.something = {};
obj.something.aValue = 5;
Or, you can also do it in fewer shots, depending what you're doing:
let obj = {
something: {
aValue = 5;
}
};

Is there a way to loop this?

Is there a way to loop a declaration of a variable? just a loop to help me declare the variables so i dont have to do the monotonous work of change the numbers of the variable
var height1 = document.getElementById('height1').value;
var height2 = document.getElementById('height2').value;
var height3 = document.getElementById('height3').value;
var height4 = document.getElementById('height4').value;
var height5 = document.getElementById('height5').value;
var height6 = document.getElementById('height6').value;
var height7 = document.getElementById('height7').value;
var height8 = document.getElementById('height8').value;
var height9 = document.getElementById('height9').value;
var height10 = document.getElementById('height10').value;
var height11 = document.getElementById('height11').value;
var height12 = document.getElementById('height12').value;
var height13 = document.getElementById('height13').value;
var height14 = document.getElementById('height14').value;
var height15 = document.getElementById('height15').value;
var height16 = document.getElementById('height16').value;
This is not a right way of coding that, Just do like,
var heights = [];
Array.from(document.querySelectorAll("input[id^=height]")).forEach(function(itm){
heights.push(itm.value);
});
And now you can iterate the array heights to manipulate the values as per your requirement.
The logic behind the code is, querySelectorAll("input[id^=height]") will select the input elements that has id starts with the text height. Since the return value of querySelectorAll is a nodelist, we have to convert it as an array before using array functions over it. So we are using Array.from(nodelist). That will yield an array for us. After that we are iterating over the returned array by using forEach and pushing all element's value into the array heights.
This is almost always an indication that you want an array. Something like this:
var heights = [];
for (var i = 1; i <= 16; i++) {
heights.push(document.getElementById('height' + i).value);
}
Then you can reference a value from the array with something like:
heights[1]
Though technically since in JavaScript your window-level variables are indexable properties of the window object, you can essentially do the same thing with variable names themselves:
for (var i = 1; i <= 16; i++) {
window['height' + i] = document.getElementById('height' + i).value;
}
Then you can still use your original variables:
height1
Though in the interest of keeping things outside of window/global scope, maintaining the array seems a bit cleaner (and semantically more sensible).
This seems to be a good use case for an object:
var heights = {};
for (var i = 1; i <= 16; i++) {
heights[i] = document.getElementById('height' + i).value;
}
Maybe its time to introduce function:
Generally speaking, a function is a "subprogram" that can be called by code external (or internal in the case of recursion) to the function. Like the program itself, a function is composed of a sequence of statements called the function body. Values can be passed to a function, and the function will return a value.
function getHeight(id) {
return document.getElementById(id).value;
}
Call with the wanted id and use it like a variable.
getHeight('height1')
Normally you would put them in an array.
var heights = []
for (i = 1; i < 17; i++) {
heights[i] = document.getElementById('height' + i).value;;
}
Beware this will give you a hole at the start of the array ie heights[0] has nothing in it. If you use this to iterate it won't matter...
for (var i in heights) {
alert(heights[i]);
}

How to use contents of array as variables without using eval()?

I have a list of variables or variable names stored in an array. I want to use them in a loop, but I don't want to have to use eval(). How do I do this? If I store the values in an array with quotes, I have to use eval() on the right side of any equation to render the value. If I store just the variable name, I thought I'd be storing the actual variable, but it's not working right.
$(data.xml).find('Question').each(function(){
var answer_1 = $(this).find("Answers_1").text();
var answer_2 = $(this).find("Answers_2").text();
var answer_3 = $(this).find("Answers_3").text();
var answer_4 = $(this).find("Answers_4").text();
var theID = $(this).find("ID").text();
var theBody = $(this).find("Body").text();
var answerArray = new Array();
answerArray = [answer_1,answer_2,answer_3,answer_4,theID,theBody]
for(x=0;x<=5;x++) {
testme = answerArray[x];
alert("looking for = " + answerArray[x] + ", which is " + testme)
}
});
You can put the values themselves in an array:
var answers = [
$(this).find("Answers_1").text(),
$(this).find("Answers_2").text(),
$(this).find("Answers_3").text(),
$(this).find("Answers_4").text()
];
for(x=0;x<=5;x++) {
alert("looking for = " + x + ", which is " + answers[x])
}
EDIT: Or even
var answers = $(this)
.find("Answers_1, Answers_2, Answers_3, Answers_4")
.map(function() { return $(this).text(); })
.get();
If your answers share a common class, you can change the selector to $(this).find('.AnswerClass').
If you need variable names, you can use an associate array:
var thing = {
a: "Hello",
b: "World"
};
var name = 'a';
alert(thing[name]);
This would make it easier to get the array populated.
var answers = new Array();
$("Answers_1, Answers_2, Answers_3, Answers_4", this).text(function(index, currentText) {
answers[index] = currentText;
});
As others have mentioned, if you can put the variables in an array or an object, you will be able to access them more cleanly.
You can, however, access the variables through the window object:
var one = 1;
var two = 2;
var three = 3;
var varName = "one";
alert(window[varName]); // -> equivalent to: alert(one);
Of course, you can assign the varName variable any way like, including while looping through an array.

Categories

Resources