[JavaScript] Knowledge you need to know before interview (keep updating)
Tags: javascript, beginners, computerscience
Published: 2020-06-09 05:06:30

Aloha Everyone. This post will helps me keep track my learning progress and mark down some key concepts. Hope everyone enjoy life and have promising job~~~

#### Question1: undefine ReferenceError
```javascript
var y = 1;
if (function f() { }) {
    y += typeof f;
}
console.log(y); //1undefined

var k = 1;
if (1) {
    eval(function foo() { });
    k += typeof foo;
}
console.log(k); //1undefined because eval(function f(){}) returns function f(){} (which is true). 

var k = 1;
if (1) {
    function foo() { }; //function must declare first not in if statement
    k += typeof foo;
}
console.log(k);//1function
```

```javascript
function sayHi() {
    console.log(name); //undefined
    // console.log(age);  //ReferenceError
    var name = 'UU';
    let age = 25;
}
sayHi();
```
Explain: var gets hoisted (memory space is set up during the creation phase) with the default value of undefined, until we actually get to the line where we declare the variable. 
let or const are hoisted, but dont get intialized. They are not accessible before declare them.


#### Question2: Closure
```javascript
var globalVar = "abc";
// Parent self invoking function 
function outerFunction(outerArg) { // begin of scope outerFunction
    // Variable declared in outerFunction function scope 
    var outerFuncVar = 'x';
    // Closure self-invoking function 
    function innerFunction(innerArg) { // begin of scope innerFunction
        // variable declared in innerFunction function scope
        var innerFuncVar = "y";
        console.log(
            "outerArg = " + outerArg + "\n" +
            "outerFuncVar = " + outerFuncVar + "\n" +
            "innerArg = " + innerArg + "\n" +
            "innerFuncVar = " + innerFuncVar + "\n" +
            "globalVar = " + globalVar);
    }// end of scope innerFunction)(5); // Pass 5 as parameter 
    innerFunction(5)  //call inner function
}// end of scope outerFunction )(7); // Pass 7 as parameter 


outerFunction(7)
```
Explain:A closure is a function defined inside another function (called the parent function), 
and has access to variables that are declared and defined in the parent function scope.
The closure has access to variables in three scopes:
Variables declared in their own scope
Variables declared in a parent function scope
Variables declared in the global namespace


#### Question3: var, let scope
```javascript
for (var i = 0; i < 3; i++) {
    setTimeout(() => console.log(i), 1); //3 3 3 
}

for (let i = 0; i < 3; i++) {
    setTimeout(() => console.log(i), 1); //0 1 2
}
```
Explain: <code>setTimeOut</code> callback function is called after the loop has been executed. *var* is global, *let* is block-scoped

```javascript
let great;
gret = {};
console.log("test typo ", gret); //{}
```
Explain: *gret* acts as global.gret={} (or window.gret={} in browser). Can use 'use strict' avoid this. If change *gret* into *great* in console, will get <code>undefined</code>

###Question4: Class static Prototype
```javascript
class BedSheet {
    static colorChange(newColor) {
        this.newColor = newColor;
        return this.newColor;
    }

    constructor({ newColor = 'green' } = {}) {
        this.newColor = newColor;
    }
}

const silkSheet = new BedSheet({ newColor: 'purple' });
console.log(silkSheet.colorChange('orange')); 
```
Explain:The colorChange function is static. Static methods are designed to live only on the constructor in which they are created, 
and cannot be passed down to any children. 
Since freddie is a child, the function is not passed down, 
and not available on the silkSheet instance: a TypeError is thrown.
If remove *static*, works!


```javascript
function Person(firstName, lastName) {
    this.firstName = firstName;
    this.lastName = lastName;
}
const member = new Person('UU', 'HH');
// TypeError: Person.getFullName = function () {
//     return `${this.firstName} ${this.lastName}`;
// };
Person.prototype.getFullName = function () {
    return `${this.firstName} ${this.lastName}`;
};

console.log(member.getFullName());
```
Explain:If you want to add a feature to all objects at once, you have to use the prototype instead.


```javascript
function Person(firstName, lastName) {
    this.firstName = firstName;
    this.lastName = lastName;
}

const uu = new Person('UU', 'HH');
const sam = Person('Sam', 'Smith');

console.log(uu); //[works!]
console.log(sam); //undefined
```
Explain:For sam, no use 'new'. when using 'new', it refers to new empty object that we create. 
If you don't add 'new', it refers to the global object.

We said that this.firstName equals "Sam" and this.lastName equals "Smith". 
What we actually did, is defining global.firstName = 'Sam' and global.lastName = 'Smith'. 
sam itself is left undefined, since we don't return a value from the Person function.


```javascript
function People(first, last, age, gender, interests) {
    // property and method definitions
    this.name = {
        'first': first,
        'last': last
    };
    this.age = age;
    this.gender = gender;
}
//create object instance
let person1 = new People('Bob', 'Smith', 32, 'male', ['music', 'skiing']);
console.log(person1.valueOf()); //nothing to return
console.log(People.valueOf()); //return [Function: People]
```
Explain: Javascript is **Prototype-based** language. It has prototype chain. The instance's current variable will 'override' its prototype object's variable(called property shadowing).
Properties and methods which are defined on the prototype are on the Objects' constructor functions, 
not the object instances themselves.
person1(instance) -> People -> Object


###### Reference:
https://github.com/lydiahallie/javascript-questions