Performing calculations on data via json - javascript

I am trying to perform a simple addition on data I have gathered from an external source via JSON. The data I am getting is being returned as a string but is a number so I have tried using both parseInt() and Number() to no avail. I have shown a simple section of the code below:
var total_energy = 0;
var energy_val;
$.each(result.report.food.nutrients, function (i, v) {
if (v.name == "Energy"){
energy_val = v.value;
var energy = Number(energy_val);
total_energy = total_energy + energy;
console.log("energy " + energy);
console.log("totalenergy " + total_energy);
energy_val = "";
energy = 0;
}
}
The console returns the correct value for energy each time but the totalenergy value just seems to stay the same as the energy value. The sum doesn't seem to have any affect. Could anyone tell me where I am going wrong with this problem?

change console.log("energy " + total_energy); to console.log("energy " + energy);

try parseInt your values... can be this

I doubt if its due to the closure created in the loop where you are iterating over the items. Try the following code.
var total_energy = 0;
var energy_val;
$.each(result.report.food.nutrients, function (i, v) {
var item = v;
//Calling calculateEnergy() function so that each 'item' is the current instance 'v' value.
(function calculateEnergy(itemClicked))(item);
}
function calculateEnergy(itemClicked){
if(itemClicked.name == "Energy"){
energy_val = itemClicked.value;
var energy = Number(energy_val);
total_energy = total_energy + energy;
console.log("energy " + energy);
console.log("totalenergy " + total_energy);
energy_val = "";
energy = 0;
}
}
I have put comments within the code.
Update console.log() is buggy with ajax requests. So instead of logging, try creating an html div and populate the values there.

Related

Assigning a list of labels values generated from a list of objects

I have an ajax call that returns a Serialized JSON string with various keys and values within it, I want to loop through these values and assign each individual key and value to a different label, I already have 8 labels set up. (I am quite new to Javascript so any help or constructive feedback would be greatly appreciated)
Haven't tried much as I am quite new to JavaScript
var obj = response.ret.SearchCriteria;
var resultJSON = obj;
var result = $.parseJSON(resultJSON);
var count = Object.keys(result).length;
for (i = 1; i < count; i++) {
var c = $('#lbl' + [i]);
$.each(result, function(k, v) {
c.text(k + ' is ' + v);
});
};
I have 6 labels and the last item of the JSON array (String) is displayed in each label
I believe your issue is why only last item of JSON array is being displayed in each label.
This is because of c.text(k + ' is ' + v).
Here the existing text content is replaced with every iteration of 'each' loop
Instead, you can consider doing this, which will append existing content as well with $.each loop.
c.text(c.text() + k + ' is ' + v)
OR
Simply
c.append( k + ' is ' + v)
If I am wrong in my assumption, please describe your scenario more, so that we can help you out :)

JS Array Find and Replace?

I have a regular expression happening that searching for all the capitals in a document. It gathers them and puts them into an array no problem.
The issue I am having is I want to replace the items in that array to include a span around each item that was captured in the array and then display the updated result. I've tried a variety of things.
I am at a complete loss. Any help is appreciated. Here was my last attempt
var allCaps = new RegExp(/(?:[A-Z]{2,30})/g);
var capsArray = [];
var capsFound;
while (capsFound = allCaps.exec(searchInput)) {
capsArray.push(capsFound[0]);
}
//for(var x = 0; x < capsArray.length; x++){
//var test = ;
capsArray.splice(0, '<span style="color:green">'+ capsArray +'</span>');
//}
}
You can't convert an entire array's elements like that using splice - you can use .map instead:
capsArray = capsArray.map(c => '<span style="color:green">' + c + '</span>');
Do you need the results in an array? If not, you can wrap all caps in a str using a modified regex:
str.replace(/([A-Z])/g, '<span>$1</span>')
example:
'A--B--C' becomes '<span>A</span>---<span>B</span>---<span>C</span>'
if the array is needed for whatever reason:
str.split(/[^A-Z]+/g).map(x => `<span>${x}</span>`)
example:
'A--B--C' becomes ['<span>A</span>', '<span>B</span>', '<span>C</span>']
Thanks to everyone for the help.
Heres my final solution for anyone else that gets lost along the way
var allCaps = new RegExp(/(?:[A-Z]{2,30})/g);
var capsArray = [];
var capsFound;
while (capsFound = allCaps.exec(searchInput)) {
capsArray.push(capsFound[0]);
}
if(capsArray.length > 0){
resultsLog.innerHTML += "<br><span class='warning'>So many capitals</span><br>";
searchInput = document.getElementById('findAllErrors').innerHTML;
searchInput = searchInput.replace(/([A-Z]{3,30})/g, '<span style="background-color:green">$1</span>');
document.getElementById('findAllErrors').innerHTML = searchInput;
}
else {
resultsLog.innerHTML += "";
}

Displaying total array elements for array being built by form

I'm currently in a JavaScript course that is asking me to have the following happen:
User enters names one at a time into a form, then presses Submit
The names are stored into an array and output to a table
As names are entered (and added to the table), a total must update as well--based on the array, not just from counting table elements
My current issue is I'll add one name, then the total shows "1"--when I add a second name, the total displays "11"
This is currently what my JavaScript code looks like:
function displayNamesAndTotal() {
// Your code goes in here.
var userInputName = [];
var totalNamesEntered = [];
var countTotal = 0;
var firstName;
var arrayIndex;
var output;
var outputTotal;
var form;
form = document.getElementById("userFormId");
output = document.getElementById("userEntriesId");
outputTotal = document.getElementById("testId");
//userInputName[0] = form.firstname.value;
userInputName.push(form.firstname.value)
for (arrayIndex = 0; arrayIndex < userInputName.length; arrayIndex++) {
output.innerHTML += "<tr><td>" + userInputName[arrayIndex] + "</td></tr>";
countTotal += userInputName.length;
}
outputTotal.innerHTML += countTotal;
return false;
}
I've spent the past day or so trying to figure out what I'm doing wrong--and it's probably something embarrassingly easy--but I'm at a loss and could use guidance
Any suggestions?
Thanks
It looks like your total is storing a string instead of a number. Try using parseInt(number) to convert the string into a number.
Good grief, from reading the other answers from you guys I think I have it licked
for (arrayIndex = 0; arrayIndex < userInputName.length; arrayIndex++) {
tableData = "<tr><td>" + userInputName[arrayIndex] + "</td></tr>";
totalCount = userInputName.length;
}
output.innerHTML += tableData;
outputTotal.innerHTML = "<h4>Total Number of Strings: " + totalCount + "</h4>";
form.string.select();
return false;
This way the totalCount acted as the array's length when it went through the loop, then outside in the innerHTML statement I could display it and have it constantly update whenever a new string was submitted.
Thank you for all of your feedback
outputTotal.innerHTML is a string, so adding to it would concatenate the strings together. Since outputTotal.innerHTML starts out as null, add 1 to it creates "1". When you add 1 to it again, outputTotal.innterHTML is already "1", so it becomes "11".
Instead of incrementing outputTotal.innerHTML try setting the HTML to it directly.
outputTotal.innerHTML = countTotal;

How to change dynamically the index of JavaScript file according to eventlistener

I am using the following code to get the answers and questions of json file:
$(document).ready(function () {
$.getJSON("data.json", function (json) {
var anserFor1st = json.questions[0].answers;
var anserFor2nd = json.questions[1].answers; //If it's more than two use a loop
document.getElementById("content").innerHTML = JSON.stringify(anserFor1st) + "<br/>" + JSON.stringify(anserFor2nd);
var aString = "";
Object.keys(anserFor1st).forEach(function (k) {
aString += anserFor1st[k] + "<br/>";
});
Object.keys(anserFor2nd).forEach(function (k) {
aString += anserFor2nd[k] + "<br/>";
});
document.getElementById("content").innerHTML = aString;
});
});
Instead I want to change dynamically the index of the answers&question, aka write the following:
var anser = json.questions[i].answers;
I have to change the index according to event-listener to clicking next and forward buttons in the html file.
How do I change the index dynamically?
I think you mean you want this:
$(document).ready(function () {
$.getJSON("data.json", function (json) {
var answers = [];
var aString = "";
for (var i = 0; i < json.questions.length; i++)
{
answers[i] = json.questions[i].answers;
document.getElementById("content").innerHTML += JSON.stringify(answers[i]) + "<br/>";
for (var j = 0; j < answers[i].length; j++)
{
aString += answers[i][j] + "<br/>";
}
}
document.getElementById("content").innerHTML = aString;
});
});
This code does exactly what yours did, but there are some things in there that make no sense (such as first loading the json.questions[i].answers into the content element, only to then replace it a few lines later with the contents of aString.) You also stringify the JSON before placing it into the DOM, but I'd have expected you to do the opposite (parsing it, since you already just retrieved it as JSON, so stringifying it again shouldn't do anything).
Basically, I'm not entirely sure what you mean by your question, so if I misunderstood please clarify your question.
EDIT: if your problem is just remembering which question you're on, make a variable to hold the number of the current question (e.g. var currentQuestion = 1;), and then just change that based on what button is clicked.
For example:
$("#buttonPrevious").on("click", function (e)
{
currentQuestion--;
});
$("#buttonNext").on("click", function (e)
{
currentQuestion++;
});
Of course you can check for minimum/maximum question numbers (for example, your max number of questions can be equal to the last value of i in the loop above).

using localStorage to keep a count

var nicWinsVsMac;
if (tempresult === win) {
wincount = JSON.parse(localStorage.getItem (playerName + 'wincount'));
wincount += 1;
localStorage.setItem(playerName + 'wincount', wincount);
winsvsopponent = 'WinsVs' + opponent;
winsvsopponent = JSON.parse(localStorage.getItem(playerName + 'WinsVs' + opponent));
winsvsopponent += 1;
console.log(winsvsopponent);
localStorage.setItem(playerName + 'WinsVs' + opponent, 'winsVs' + opponent);
console.log(localStorage.getItem(nicWinsVsMac));
}
playerName and opponent are parameters passed in. In this case, playerName = 'nic' and opponent = "Mac"
My browser is giving me "unexpected token w" on the line where i parse out the localStorage. I cannot figure out what is going on. Any help would be great. Thanks!
Instead of using a separate localStorage variable for each attribute of the player. Why not store all the players attributes in a single object and then save that to localStorage.
For example, you can do the following:
var player = new Object();
player.name = 'Mac';
player.winCount = 3;
player.winAgainst = new Array();
localStorage.setItem(player.name, JSON.stringify(player));
var player1 = JSON.parse(localStorage.getItem(player.name));
console.log(player1.name + " has " + player1.winCount + " wins.");
This allows you to save all the player's attributes to a single localStorage variable making it much easier to read and write from.
In regards to the error you are recieving, I believe the issue with your code is that you are not using JSON.stringify in the call to setItem.

Categories

Resources