简体   繁体   中英

Javascript “if” Order of Operations

So let's say you have a really basic person object with two values and one function:

function personObject() {
    this.name = 'First Name';
    this.placeInLine = 1;
    this.setPlaceInLine = function(place) {
        this.placeInLine = place;
    }
}

And we setup some variables like this:

var john = new personObject();
var bill = new personObject();
var message = "";

Now look at the three codes snippets below...

---Code #1---

if(john.placeInLine < bill.placeInLine) message = "John is before Bill";
else message = "John is not before Bill";

RESULT: message = "John is not before Bill"; // because 1 is not less than 1

---Code #2---

bill.setPlaceInLine(2); // change Bill's place to 2 (instead of default of 1)
if(john.placeInLine < bill.placeInLine) message = "John is before Bill";
else message = "John is not before Bill";

RESULT: message = "John is before Bill"; // because 1 less than 2;

---Code #3---

if(john.placeInLine < bill.setPlaceInLine(2)) message = "John is before Bill";
else message = "John is not before Bill";

RESULT: message = "John is not before Bill": // why?

Is the .setPlaceInLine function being called after the comparison? Or is the act of running that function returning something that is then being compared to john.placeInLine?

Because setPlaceInLine method has no explicit return, and therefore returns undefined . And 1 < undefined evaluates to false : undefined gets converted to Number , giving NaN , and 1 < NaN is certainly false ( 1 > NaN is false too, btw).

While you can fix this by making your setter method return the assigned value:

PersonObject.prototype.setPlaceInLine = function(place) {
  return this.placeInLine = place;
}

... I think it's better (more clean) to use the setters and getters separately (like in your code #2 example).

As a sidenote, I'd recommend using prototypes to set up object methods (like I did in my example code). The reason for this is pretty well explained in this answer : basically with prototypes you will make just a single Function entity, used by all the created objects, when with this.someMethod you would create a new Function each time a constructor is called.

You are comparing to the returnvalue of the function.

Unless you actually return a value via return this.placeInLine; it will compare to the undefined always resulting in false .

Change your code to this:

this.setPlaceInLine = function(place) {
    return this.placeInLine = place;
}

setPlaceInLine returns nothing. And nothing is evaluated as less than 1. You could update setPlaceInLine to return the value:

function personObject() {
    this.name = 'First Name';
    this.placeInLine = 1;
    this.setPlaceInLine = function(place) {
        this.placeInLine = place;
        return place;
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM