Javascript - json data not being transferred into memory properly - javascript

I have a json file that contains 16,490 lines of data. Here's a snippet:
[
...
["alrightty",2 ],
["alrighttyy",1 ],
["alrighty",100 ],
["alrightyy",1 ],
["alrigt",1 ],
...
]
This data will be used for my sentiment analysis thesis project. I used the following code to extract the data from the json file:
var positive_words_list = {}
function readJSONFile(filename,type) {
$.ajax({
type: 'GET',
url: filename,
dataType: 'json',
success: function(data) {
switch (type) {
case "pos" : positive_words = data; break;
case "neg" : negative_words = data; break;
case "afinn" : afinn_words = data; break;
}
},
async: false
});
}
readJSONFile('js/json/positivekeywords.json','pos');
for (var i = 0; i < positive_words.length; i++) {
row = positive_words[i];
positive_words_list[row[0]] = row[1];
};
What this code does is extract the data from the json file and then put it in a 1-dimensional array with each word as an array index and the number as the value.
Now I have this code run when the site loads inside $(function() { ... }); so positive_words_list should contain the data on load time. The thing is after the site loads and I do positive_words_list.length in the console, it outputs 63. As I said, there should be 16,490 entries.
Did I miss something? What am I doing wrong?
Thanks!
John
EDIT: I should add that when I do a positive_words.length in the console, I get the correct number of elements, 164,950

As far as I can see positive_words_list is a JavaScript object that does not have length property out of the box. So the only reason why you get the magic number 63 is because your array of arrays contain entity with word length as a first item; something like:
[
...
['length', 63],
...
]
In order to get number of keys in JavaScript Object you can either do Object.keys(positive_words_list).length or iterate over all properties and increment the counter:
function size(obj) {
var key,
counter = 0;
for(key in obj) {
if(obj.hasOwnProperty(key)) {
counter++;
}
}
return counter;
}
size(positive_words_list); // <- will return number of properties in object
Your snippet may be modified in the following manner:
HTML
<h1 id="data">Number of positive words is ...</h1>
JavaScript
$(function(){
var positive_words,
positive_words_list = {};
function readJSONFile(filename,type) {
$.ajax({
type: 'GET',
url: filename,
dataType: 'json',
success: function(data) {
switch (type) {
case "pos" : positive_words = data; break;
case "neg" : negative_words = data; break;
case "afinn" : afinn_words = data; break;
}
},
async: false
});
}
readJSONFile('data.json','pos');
for (var i = 0; i < positive_words.length; i++) {
row = positive_words[i];
positive_words_list[row[0]] = row[1];
};
$('#data').html('Number of positive words is ' + Object.keys(positive_words_list).length);
});
Plunker: http://plnkr.co/edit/uhHZ1zEuUHXHIQrd1BVa?p=preview

positive_words_list is an object, not an array, so you should result in:
positive_words_list["alrightty"] === 2
positive_words_list["alrighttyy"] === 1
and so forth. You can get an array of the keys of the object using:
Object.keys(positive_words_list)
Object.keys(positive_words_list).length
Which will return an array of the keys of your object. Note that Object.keys is an ES5 feature available in most current browsers.

Related

Get JSON array data by field name

I'm trying to get JSON data by field name like this data.name and it return the desired data, but I have 25 fields in the array and I want to make this dynamically, using data + "." + variable, when I alert it returns [Object object].name, so how I can make it executable?
I tried many ways but all failed, please help me doing this.
$.ajax({
type: "Get",
url: "/Home/Report_Data",
datatype: "json",
dataSrc: "",
contentType: 'application/json; charset=utf-8',
data: {
'Arrnagement': Arrnagement
},
success: function(data) {
var result = getElementsById("LD_name LD_Loan_Type LD_id LD_Full_Name_AR LD_GENDER LD_BIRTH_INCORP_DATE LD_PS_MOTHER_NAME LD_Street_AR LD_TEL_MOBILE LD_EMPLOY_STATUS_D LD_EMPLYRS_Name LD_MARITAL_STATUS LD_PS_PL_OF_BIR_AR LD_wifeName LD_Effective_Interest_Rate LD_Contract_amount LD_Repayment_Amount LD_Sector_name LD_NUM_REPAYMENTS LD_Loan_Maturity LD_Orig_Contract_Date LD_Loan_CCY LD_Arrangement LD_COLLATERAL_TYPE LD_Description LD_COLLATERAL_VALUE LD_COLLATERAL_Currency LD_GUARANTOR_ID LD_NATIONALITY LD_G_Full_Name_En LD_G_DATE_OF_BIRTH LD_G_PLACE_OF_BIRTH LD_G_MOTHER_NAME_EN LD_HOUSING_LOAN_AREA_CLASS LD_HOUSING_PROPERTY_NATURE LD_HOUSING_LOAN_PURPOSE LD_HOUSING_PROPERTY_AREA");
var jid;
for (var i = 0; i < result.length; i++) {
jid = (result[i].id.substring(3));
var resulting = data[0].jid;
alert(resulting);
if (result[i].innerHTML = data[0].jid != "undefined") {
result[i].innerHTML = data[0].jid;
} else {
result[i].innerHTML = "";
}
}
//jid = name;
//data[0].name returns "Joun"
//data[0]+"."+jid returns [object object].name but i need it to return "Joun"
This should work. I changed the dot notation while accessing the object property.
$.ajax({
type: "Get",
url: "/Home/Report_Data",
datatype: "json",
dataSrc: "",
contentType: 'application/json; charset=utf-8',
data: { 'Arrnagement': Arrnagement },
success: function (data) {
var result = getElementsById("LD_name LD_Loan_Type LD_id LD_Full_Name_AR LD_GENDER LD_BIRTH_INCORP_DATE LD_PS_MOTHER_NAME LD_Street_AR LD_TEL_MOBILE LD_EMPLOY_STATUS_D LD_EMPLYRS_Name LD_MARITAL_STATUS LD_PS_PL_OF_BIR_AR LD_wifeName LD_Effective_Interest_Rate LD_Contract_amount LD_Repayment_Amount LD_Sector_name LD_NUM_REPAYMENTS LD_Loan_Maturity LD_Orig_Contract_Date LD_Loan_CCY LD_Arrangement LD_COLLATERAL_TYPE LD_Description LD_COLLATERAL_VALUE LD_COLLATERAL_Currency LD_GUARANTOR_ID LD_NATIONALITY LD_G_Full_Name_En LD_G_DATE_OF_BIRTH LD_G_PLACE_OF_BIRTH LD_G_MOTHER_NAME_EN LD_HOUSING_LOAN_AREA_CLASS LD_HOUSING_PROPERTY_NATURE LD_HOUSING_LOAN_PURPOSE LD_HOUSING_PROPERTY_AREA");
var responseData = data[0];
var jid;
for (var i = 0; i < result.length; i++) {
jid = (result[i].id.substring(3));
var resulting = responseData[jid];
alert(resulting);
if (responseData[jid]) {
result[i].innerHTML = responseData[jid];
}
else {
result[i].innerHTML = "";
}
}
Try giving data[0][jid], we can give a variable in brackets also inorder to get the data
Hope it works
If do foo.bar you are getting a property with the name 'bar' on object foo. If you have some variable const bar = "qux" and you want to access property on some object with the same name as bar value /"qux"/ you just need to use square brackets - foo [bar], which will be the same as calling foo.qux; So, in your case you just need to use data[0][jid] instead of data [0].jid, supposing jid contains a string that is also a key in data[0].
You can just do data[0][variableName] and this will return the data you want. for example. If data had a json string [{ "Name" : "Jane Doe"}] You could execute it like this.
var variableName = "Name";
console.log(data[0][variableName])
This would return "Jane Doe".
if you have your field names in an array you can loop through them using $.each or a for loop.
For example say your json string is [{"First_Name" : "Jane", "Last_Name" : "Doe", "Age" : 32}] you could get all the values from the json string doing this.
var FieldNames = ["First_Name" , "Last_Name", "Age"]
$.each(FieldNames, function(i,item) {
console.log(data[0][item])
}
OR
var FieldNames = ["First_Name" , "Last_Name", "Age"]
for(var i = 0; i < FieldNames.length; i++) {
console.log(data[0][FieldNames[i]])
}

JSON.stringify and $http request

I have a JS String, like so:
user_fav = "21,16";
This has to go thru a function where it becomes a JSON array with an id key, like so:
{"id":21},{"id":16}
And this goes into an $http request:
return $http({
method: 'GET',
url: getUrl('products'),
params: {
pageSize: 2000,
pageNumber: 1,
"filter": { "q": { "$or": [{"id":21},{"id":16}] } }, // <-- HERE
sort: []
}
});
Now if I run the above $http request everything works fine, but if I convert the String (user_fav) into that JSON and send this to the $http request it fires an error. This is my converter:
user_fav = "21,16";
var user_fav_to_array = "";
var splitFav = user_fav.split(",");
for (var i = 0; i < splitFav.length; i++) {
user_fav_to_array += JSON.stringify({ id: parseInt(splitFav[i]) }) + ',';
}
var JSONFavs = user_fav_to_array.substring(0, user_fav_to_array.length - 1);
//Result: JSONFavs => {"id":21},{"id":16}
So this gives an error:
return $http({
method: 'GET',
url: getUrl('products'),
params: {
pageSize: 2000,
pageNumber: 1,
"filter": { "q": { "$or": [JSONFavs] } }, // <-- HERE
sort: []
}
});
Madame and messier the error is 417 (Critical Exception), this is coming from the Backand.com syste
Have a look at the code below. What your code actually doing is assigning a Json STRING to $or property. But really needed is to assign array of items (as expected). Let me know if you have any questions
user_fav = "21,16";
//Dont need this
//var user_fav_to_array = "";
// New Variable to save array items
var arrayData =[];
var splitFav = user_fav.split(",");
for (var i = 0; i < splitFav.length; i++) {
// don't need this
//user_fav_to_array += JSON.stringify({ id: parseInt(splitFav[i]) }) + ',';
// Just create a simple javascript object with id and put it into array at i index
arrayData[i]={ id: parseInt(splitFav[i]) };
}
//var JSONFavs = user_fav_to_array.substring(0, user_fav_to_array.length - 1);
// Then in Http Request filter, it should be just like this "$or": arrayData
"filter": { "q": { "$or": arrayData } }
This might have to deal with your variable - var user_fav_to_array = "";
You may want to change it to the following var user_fav_to_array = [];
Since it has the quotations it may be causing your variable to behave in a way that you don't want it to. Unless strings are treated as arrays in javascript.

Storing ajax response data into array and compare it to the last values

I am stuck with these. I want to create a function to be run every 4secs. Now My function will get all the queue_id from my database and store it in array again and again, after storing it, i will compare it again and again every 4 secs, if there are changes , then i will do something.
Example execution : If my database response with queue_id's: 1,2,3,4,5 then i will store these data from an array. After storing it, i will query again evry 4 seconds if it returns 1,2,4,5 or 1,2,3,5 i will do something, but if it returns thesame like 1,2,3,4,5 then i will not do something.
I have no idea how to store or create array in javascript . Please help me:
function check_getqueue(clinicID, userID) {
$.ajax({
url: siteurl+"sec_myclinic/checkingUpdates/"+clinicID+"/"+userID,
type: "POST",
dataType: "JSON",
success: function(data) {
for(var i=0;i<data.length;i++) {
var tmpCountQ = data[i]['queue_id'];
};
if (tmpCountQ < lastcountQueue) {
}
lastcountQueue = tmpCountQ;
}
});
}
You need to keep track of the lastly received set of ids and compare them with the new ones. When a difference found, call your doSomething() and update the record for next run.
To get things faster you can first check the lengths. More info in the comment blocks below.
var previousQueueIDs = [];
function doSomething() {
// do something
// ...
// set timer for the next run
setTimeout(check_getqueue, 4000);
}
function check_getqueue(clinicID, userID) {
$.ajax({
url: siteurl+"sec_myclinic/checkingUpdates/"+clinicID+"/"+userID,
type: "POST",
dataType: "JSON",
success: function(data) {
var queueIDs = [];
if(previousQueueIDs.length != data.length) {
previousQueueIDs = queueIDs;
return doSomething();
}
// length didn't change, so check further
// create new array for the current values
for(var i=0;i<data.length;i++) {
queueIDs.push(+data[i]['queue_id']);
};
// sort them for faster comparison
queueIDs.sort( function(a,b) {
return a-b;
});
// check one by one and exit to run doSomething
// as soon as the first difference found
for(var i=0; i<queueIDs.length; i++) {
if(queueIDs[i] != previousQueueIDs[i]) {
previousQueueIDs = queueIDs;
return doSOmething();
}
}
// no difference this time, just set timer for the next run
setTimeout(check_getqueue, 4000);
}
});
}
Use push, and declare the array outside the ajax request. now all working
function check_getqueue(clinicID, userID) {
var tmpCountQ = [];
var lastCon = [];
$.ajax({
url: siteurl+"sec_myclinic/checkingUpdates/"+clinicID+"/"+userID,
type: "POST",
dataType: "JSON",
success: function(data) {
for(var i=0;i<data.length;i++) {
tmpCountQ.push(data[i]['queue_id']);
};
if(typeof lastCon[0] != "undefined")
{
for(j=0;j < tmpCountQ.length;j++)
{
if(tmpCountQ[j] != lastCon[j])
{
lastCon[j] = tmpCountQ[j];
}
}
}
else
{
lastCon = tmpCountQ;
}
console.log(tmpCountQ);
}
});
}

How to add items to an empty array in Javascript

Controller sends a JSON for one Frame. I need to keep incrementing the array where Multiple Frame's score gets added. For example
FrameScore = f1 + f2 +.. lastF
Issue The values do not get added and shows data for each Frame only. Where am I doing it wrong?
var bowlingData = {
"frames": []
};
var frames = [];
$('#submitButton').click(function(e) {
frames.push([$("#FirstRoll").val(), $("#SecondRoll").val()]);
for (var ln = 0; ln < frames.length; ln++) {
var temp = {
"firstroll": $("#FirstRoll").val(),
"secondroll": $("#SecondRoll").val()
};
bowlingData.frames.push(temp);
}
console.log("temp data: " + temp);
bowlingData.frames.push(temp);
var element = this;
$.ajax({
url: "/Home/Submit",
type: "POST",
data: JSON.stringify(bowlingData),
dataType: "json",
traditional: true,
contentType: "application/json; charset=utf-8",
success: function(data) {
var parseData = JSON.parse(data);
console.log("MyDate: " + data.score);
console.log("Parse" + parseData);
$("#lblTotalScore").text(parseData.score);
$("#FirstRoll").val("");
$("#SecondRoll").val("");
},
error: function() {
alert("An error has occured!!!");
}
});
});
Apparently the solution is
var frameArray= [];
frameArray.push("#FirstRoll");
frameArray.push("#SecondRoll");
But that is to add single elements to the array. If the input is [[2, 3],[4, 5],...] then the JSON object representation would be
{ "frames": [{"first": 2, "second": 3}, {"first": 4, "second": 5}, ... ] }
However, there was another issue of not getting the correct response from the controller.
The issue here is that an empty array is created (i.e. frames) and on the 3rd line the value was pused to the empty Array. Although the the for loop was adding each element to the Array(i.e. frames) but when the response was created the recent input was replacing the previous input, because the JSON object bowlingData was holding temp data only. So no need to create any Array to increment multiple input result. Initial value would be hold by the browser and second input would be added in next submit.
Was
var frames = [];
$('#submitButton').click(function(e) {
frames.push([$("#FirstRoll").val(), $("#SecondRoll").val()]);
for (var ln = 0; ln < frames.length; ln++) {
var temp = {
"firstroll": $("#FirstRoll").val(),
"secondroll": $("#SecondRoll").val()
};
bowlingData.frames.push(temp);
}
Should be
$('#submitButton').click(function (e) {
bowlingData.frames.push({
"firstroll": $("#FirstRoll").val(),
"secondroll": $("#SecondRoll").val()
});

Setting Localstorage Variable Name to a Variable's value

I am using a javascript loop to create localstorage variables. For some reason, all the localstorage values are null except for the last one. Does anyone know why?
Here is my code:
function setValues() {
var json = jQuery.parseJSON(data);
for (var i=0; i<json.length; i++)
{
var id = json[i].id;
$.ajax({
url: url,
crossDomain: true,
type: 'post',
data: {
'theid': id
},
success: function (data2) {
window.localStorage['club'+id] = data2;
},
});
}
}
function getValue(id) {
console.log(window.localStorage.getItem('club'+id));
}
I call getValue() else where in the code, it is irrelevant to the issue. If the 'id' is the last id that was used for adding to the localstorage, it isn't null. However, it seems as if all the previous values are overwritten.
How can I fix this issue? Any help would be appreciated. Thanks!
ANSWER REWRITE BASED UPON THE OP's QUESTION CHANGE
This is actually a very common JavaScript issue and almost impossible to search for unless you already know the answer the magic words involved.
Because your wording is slightly different than the usual issue, I'm not going to vote to close this question but rather, explain what is going on.
There is only one copy of the variable i and that variable is changed as the loop runs. By the time the callbacks return, that loop is long over and i has reached its final value.
What you need to do is capture a local copy of that value. There are two ways to do it -- I'll show the easiest one to read:
function doAjax(i) {
// this 'i' is private.
var id = json[i].id;
$.ajax({
url: url,
crossDomain: true,
type: 'post',
data: {
'theid': id
},
success: function (data2) {
window.localStorage['club' + id] = data2;
}
});
}
function setValues() {
var json = jQuery.parseJSON(data);
for (var i = 0; i < json.length; i++) {
doAjax(i);
}
}
The other way to do this is to use a closure and an anonymous function:
function setValues() {
var json = jQuery.parseJSON(data);
for (var i = 0; i < json.length; i++) {
(function (i2) {
// this 'i' is private.
// Givign it the name of 'i2' just to be clear
var id = json[i2].id;
$.ajax({
url: url,
crossDomain: true,
type: 'post',
data: {
'theid': id
},
success: function (data2) {
window.localStorage['club' + id] = data2;
},
});
// this is the 'i' from the main loop
}(i));
}
}
For more info see
How do JavaScript closures work?

Categories

Resources