Apply function javascript looping extra - javascript

I'm a newbie to Javascript and created a sample function to test the apply function of the javascript.
I need couple of clarification on this code,
value -x will take the first array ['val1','val2'] but just wondering it substitutes to (this,x)..
2.I see a 3 items being printed in the console.log, the last item being - undefined, undefined, What that happends
var dummyfunction1 = function(val1,val2){
console.log(array1,array2);
};
[['val1','val2'],['val3','val4']].forEach(function(x){
dummyfunction1.apply(this,x);
});
dummyfunction1()

There are a couple of issues here.
dummyfunction1 is using variable that are undefined in the body. It should be this:
var dummyfunction1 = function(val1,val2){
console.log(val1,val2);
};
The last line dummyfunction1() is making an additional call to the dummyfunction1 with no parameters. This is the undefined undefined you are seeing.
The full code should be this:
var dummyfunction1 = function(val1,val2){
console.log(val1,val2);
};
// this will automatically be run, no need to call dummyfunction1 on your own after this
[['val1','val2'],['val3','val4']].forEach(function(x){
dummyfunction1.apply(this,x);
});

Related

Issues with populating arrays from csv(dsv) parsing

I am quite new to javascript, basically using it for the first time to write a histogram plotter application. My issue is, I am importing a data file and ideally sending (some of) the entries into an array. Problem is that once I do that, I have troubles accessing the entries in my array.
How could I fix that? Posting the code below in case it helps.
Thank you!
let filename = 'uploads/testdata.dat';
const data_e = new Array();
d3.dsv(" ",filename, (event)=>{
data_e.push(event.mass);
return data_e
})
console.log(data_e);
Which outputs
Array []
​
0: "734.770828169"
​
1: "85.0912893849"
​
2: "87.383924186"
​
...
However if I wanna get a value:
console.log(data_e[0]) //output: undefined
Edit1: the values I'm pushing are in console.log(event.mass).
output:
734.770828169 analyzer.php:19:12
85.0912893849 analyzer.php:19:12
87.383924186 analyzer.php:19:12
(...)
Edit2: If I call console.log(data_e) inside the dsv function I get a line for each iteration while my array gets filled, ending with
Array(7178) [ "734.770828169", "85.0912893849", "87.383924186", "1274.99805502", "91.5349415148", "80.2766459668", "1396.69489276", "91.5584443363", "94.52017453", "1582.29197222", … ]
Which is, indeed the object I want to get. But what if I want to carry that outside the function dsv(), so that I get the same output as above?
Edit3: Calling console.log(JSON.stringify(event.mass)) gives:
again, one line for each 'iteration' (I think), and it makes sense. I just want to use the full array outside that function (or maybe it's just a silly thing to do .-.)
"734.770828169" analyzer.php:19:12
"85.0912893849" analyzer.php:19:12
"87.383924186" analyzer.php:19:12
"1274.99805502" analyzer.php:19:12
(...)
Do not use return inside the loop, because you then leave it immediately. Whatsmore, I think d3.dsv() is an asynchronous function. Means your console log outside this method must return undefined as Javascript does not wait for d3.dsv() to finish. And your Array data_e is currently undefined.
let data_e = new Array();
Instantiate it this way and you'll see, that console.log() will output [] instead of undefined.
let data_e = [];
d3.dsv(" ",filename, (event)=>{
// your code
})
console.log(data_e);
Actually, I could not find a manual about how to get a trigger when d3.dsv() is finished. But fo the start try it this way. It's not perfect but it's only supposed to show you that it actually works;
let filename = 'uploads/testdata.dat';
const data_e = new Array();
// run the filter
d3.dsv(" ",filename, (event)=>{
data_e.push(event.mass);
})
// wait 2 seconds, then show the array in the console
setTimeout( () => {
console.log(data_e);
}, 2000);

How to determine if an array of string objects is empty using ngIf?

I have to write a code in which I must transfer some items between two lists and hide an error when the array of object literals to be transferred to isn't empty. I have created two controllers(to manage two separate lists) and one service to deal with common data. A list has been defined inside the service along with some functions to transfer items from one list to another. The array size never seemed to change from 0,which is the logic i am trying to use in ngIf.
My logic was to check if the array is empty, then return a value of true if it was empty and set a variable empty in the controller. Then in ng-if I will check ng-if="b.empty" and thought that that would work but it didnt. The array size would remain 0 all throughout the life cycle of my code. I used ._isEmpty(list),angular([],[]) and the most obvious, array.length but the issue was initially they showed 0, but then the array size never changed. Even after populating the target array, the size seemed to stay 0 with any/all of the above functions/methods.
l1.$inject = ['listService']
function l1(listService){
var buying = this;
buying.items = listService.display();
buying.Add = function ($index){
listService.addItem($index);
}
}; //This is the controller for the source array.
.
.
.
bought.empty = listService.checkIfFull(); //Part of the second controller which assigns empty a boolean value
.
.
.
service.checkIfFull = function (){
if(blist.length == 0){
console.log(_.isEmpty(blist))
console.log(tblist)
return false;
}
else
{
console.log("not going here");
return true;
}
}; //The service checks if the array is empty
<div class="emptyMessage" ng-if="b.empty">Nothing bought</div>
The value of the console.log statements also only seem to be executing in the true portion of the if statement. I found a solution for this, which was to simply check in the html tag itself, if the local list's(that I'm looping through which ng-repeat)length was equal to zero and that worked. But could you please explain why my attempt is wrong? I am a beginner to AngularJs and JS in general so i might have not understood some rules about js and thus written wrong code. Thank you.
Edit: Here's the link to the codepen-> https://codepen.io/meanmanmachineman/pen/RmmdjY
Your problem is caused by the line bought.empty = listService.checkIfFull();. There you are calling to the function listService.checkIfFull() and assigning the returned value to bought.empty. What you should do is to assign the function itself to bought.empty:
bought.empty = listService.checkIfFull;
This way each time bought.empty is evaluated, it returns the current real value.
EDIT:
I'll try to be more explicit about the difference between, bought.empty = listService.checkIfFull() and bought.empty = listService.checkIfFull.
The first way, bought.empty will call to listService.checkIfFull() and store the returned value as a static value and any time the variable is evaluated, the value will be the same.
By using the other method, the value of bought.empty is not a number but the listService.checkIfFull function itself. This way, each time AngularJS evaluates the variable, the function is executed and returns the corresponding value.

Meteor cursor.fetch().property returns "undefined"

I have a simple helper that returns an array to an #each block inside my template. This works ok and the tags are displaying.
However, i don't understand why i can't console.log a property of the userTags, for instance userTags.BusinessContact. But i can console.log the complete object so (console.log(userTags)) will work.
Template.profileTags.helpers({
tag:function(){
var userTags = tikiUser.find({}).fetch()
//this returns "undefined" 2 times
Meteor.setTimeout(function(){console.log(userTags.BusinessContact)}, 500)
return userTags
}
})
Why is that?
thx,
You are trying to get the BusinessContact property of an array - try doing
userTags[0].BusinessContact
PS: Try to make a meteorpad.com when posting a problem
Just try this.
if(userTags)
{
Console.log(userTags.BusinessContact)
}
In meteor some time we will not get value for the first time so,If we write a if condition than it will check the value there Only.
Hope this helps you.

Bug in console.log? [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Is Chrome's JavaScript console lazy about evaluating arrays?
I try the following code:
var myList = new Object();
var item = new Object();
item.text = "item-1";
myList[3] = item;
console.log(myList);
console.log(myList[3].text);
// Assign another object to the same entry
var item2 = new Object();
item2.text = "item-2";
myList[3] = item2;
console.log(myList);
console.log(myList[3].text);
The result is quite odd:
* Object
* 3: Object
text: "item-2"
item-1
* Object
* 3: Object
text: "item-2"
item-2
BUT - if i execute the second part after some time (using setTimeout), and unfold the first object, I get it right, i.e.:
* Object
* 3: Object
text: "item-1"
item-1
* Object
* 3: Object
text: "item-2"
item-2
I find it important to share it, since I think one can waste a lot of time trying to understand what's wrong in his code.
And if somebody has some reference to an open bug or something - please reply this ticket.
Thanks!
My view is that this is a horrendously irritating 'feature' that I really wish I could turn off, it makes debugging a nightmare, not knowing at which point in time something may have updated an object, whilst trying to establish exact object state at a give point in the code. The feature could be useful for 'watch points' etc, but not in something called a 'LOG' (the clue is in the name).
Consider this code fragment:
var person = {'name':'Tom'};
console.log( person); //output the entire object variable
person.name = 'Thomas';
//the output is an object, whose 'name' value is 'Thomas', even though the log statement was placed before the value was changed to 'Thomas'.
AND THEN:
var person = {'name':'Tom'};
console.log( person.name); //changed to output a string variable
person.name = 'Thomas';
//the output here, however, has not dynamically updated and correctly outputs 'Tom'
this is a known bug (50316) that gets reported again and again because people don't take a look at the bugtracker before reporting:
78325
94887
105559
107828
111020
131124
sadly, theres no information about if/when this will get solved. until that moment, you'll need to clone objects before passing them to console.log().
Sounds to me more like a race condition than anything else. Since you are only passing a reference to console.log(), the value it refers it has likely changed value by the time it is actually logged. Then when you use setTimeout(), the value changes after it has been logged. Instead of passing a reference to console.log(), pass a clone of the value.
This is a known problem/feature with the console log in some browsers.
When you log something, it may not immediately be turned into text format. If the log stores a reference to the object that you log, it will be turned into text format when it's actually shown in the log.
This has the advantage that logging something has a very small impact on performance, until you actually open the log window to show the log.
Even if you have the log window open while you run the code, there is no updates happening while your function is running (as Javascript is single threaded), so the console window will show the values as they are at the end of the function, when the window is updated.
I have done some experiments with this "problem" on the latest version of Chrome 20.0.1132.57 m.To summarize the key points :-
console.log() prints a reference to the object with as "> Object" when the code is executed
The state of the object when you click on the triangle is displayed, irrespective of the line of code where the console.log() is executed
If you want to print the object in its current state, print a clone console.log(JSON.parse(JSON.stringify(obj)));
You could use this bit of code to test this on your own browser:
window.onload = function() {chto = {a : 10, b : 20};
console.log('Open this object after 5 seconds')
console.log(chto);
console.log('Open this object before 5 seconds')
console.log(chto);
console.log('Console of the cloned object')
console.log(JSON.parse(JSON.stringify(chto)));
setTimeout(function(){ console.log('5 seconds up'); chto['b'] = 30; },5000 ) ; };

Titanium Javascript: "that." does not work

Neither this nor that works. Does anyone know what is going on??
Edit:
qwerty is simply called as "qwerty();" when in other pieces of code.
It is supposed to be indepedent.
Edit: I realize what is wrong. The problem lies with the i...
function qwerty () {
..... for loop that changes i ......
var that = this;
this.chara[i] = createlabel.....
this.chara[i].addEventListener('click', function(e) {
var j = e.source.id;
alert("hello word");
alert(this.chara[j].width); // I get the error here
});
this.chara[i].addEventListener('doubleclick', function(e) {
alert("hello word");
alert(that.chara[i].width); // I get the error here too.
});
}
Any JS problem relating to this is likely due to the way the function using this is called. Storing a reference to this in your that variable should let you reference it from within your nested functions, exactly the way you are doing it already - assuming that qwerty() is called in a way that sets this to the correct object in the first place. (Personally I like to call such a variable self since it more accurately reflects what the variable is doing.)
However, in your function you say you get the error on this line:
that.chara[i].width
Given that you say this.chara[i].addEventListener(...) I'm guessing that the chara[i] variable holds a reference to a DOM element. If that is the case I'm guessing it is an element type that doesn't have a width property. Try this:
that.chara[i].style.width
https://developer.mozilla.org/en/CSS/width
That's the best I can do for you without more information about what error you're getting and how the qwerty() function is called...

Categories

Resources