Liu Niping: Wemicro front-end engineer. Raise fish raise flowers raise dog, stay up late dance disco drink. After half a life away, I returned with three years of front-end work experience.

preface

Recently free to see a bit of “JS advanced programming” in the variable and memory chapter, the variable and memory problems have been summarized, which contains some of the interview plativized questions, and interspersed with some seemingly simple but accidentally dropped into the pit of the small code questions, if you were asked in the interview, Can you make a good impression on the interviewer that you are smart? If you’re interested, keep reading.


This article covers the following points

Part I Variables

A basic data type

Eight. Null, Boolean, Number, String, symbol, bigInt, object.

1.1 Basic Types

7. Undefined, Null, Boolean, Number, String, symbol, bigInt Two of the more specific ones are explained a little.

symbol
  • Each fromSymbol()The returned symbol value is unique. A symbol value can be used as an identifier for object properties; This is the only purpose of this data type.
Symbol('1') = =Symbol('1') // false
Copy the code
  • It is incomplete as a constructor because it does not support syntax:new Symbol().
Symbol(1) //Symbol(1)
new Symbol(1) // Uncaught TypeError: Symbol is not a constructor
Copy the code

Q1. If the key of an object is created using Symbol, how to obtain all the keys of the object, name at least two?

A1.

Object. GetOwnPropertyNames Object. GetOwnPropertySymbols or Reflect. OwnKeys

Q2. What is the output of typeof Symbol and typeof Symbol()?

A2.

typeof Symbol //"function"
typeof Symbol(a)//"symbol"
Copy the code
bigInt
  • BigIntIs a numeric type of data that can represent an integer in any precision format. Designed to safely use more accurate timestamps, large integer ids, and more, are new features in Chrome 67.NumberTypes can only be represented safely- 9007199254740991 (- (2 ^ 53-1))9007199254740991 (2 ^ 53-1)Integer values outside this range may lose precision.
9007199254740991 / / 9007199254740991
9007199254740992 / / 9007199254740992
9007199254740993 / / 9007199254740992!!!!!
Copy the code
  • createBigInt

Append n to the end of the integer, or call the BigInt() constructor.

9007199254740993n //9007199254740993n
BigInt('9007199254740993') //9007199254740993n
BigInt(9007199254740993) / / 9007199254740992 n!!!!!
Copy the code
  • BigIntNumberNot exactly equal, but loosely equal.
9n= =9 
//true
9n= = =9 
//false
Copy the code

1.2 Reference Types

Object contains function, Array, Date, RegExp.

1.3 Difference between null and undefined

  • undefinedRead a variable that has not been assigned a value,nullDefines an empty object that is a placeholder for an object that does not exist
  • nullandundefinedConversion to the number data type results in different results.nullinto0.undefinedintoNaN
new Number(null)  //Number {0}
new Number(undefined) //Number {NaN}
Copy the code

Second, determine the data type

2.1 typeof

Only applicable to base data types (except null). Null, representing an empty object pointer, returns object. For objects, function returns function correctly, and all objects return object.

var a; 
console.log(a);//undefined
console.log(typeof a); //undefined
Copy the code
typeof typeof 1 //"string"
Copy the code

2.2 instanceof

Check whether A is an instanceof B. A instanceof B is used to check known object types or user-defined types.

function Beauty(name, age) {
  this.name = name;
  this.age = age;
}
var beauty = new Beauty("lnp".18);
beauty instanceof Beauty // true
Copy the code

Q1.

Object instanceof Function // true
Function instanceof Object // true
Object instanceof Object // true
Function instanceof Function // true
Copy the code
  • instanceofBe able to tell[]ArrayBut it thinks[]Is alsoObjectBecause its internal mechanism is judged by the prototype chain of the object, it will traverse the prototype chain of the left variable until it finds the prototype chain of the right variableprototypeReturn if you can find ittrue.
  • instanceofCannot judge created by literalsBoolean.Number.StringType, but can judge bynewThe instance created by the operator.
  • instanceofYou can determine the type of reference created by the literalArray.Object.

2.3 the constructor

The constructor property returns a reference to the array function that created this object.

  • constructorCan’t be used for judgmentundefinednullBecause they don’t have constructors.

In the utility scenario applet, WXS does not support the use of Array objects, so we cannot use [] instanceof Array, and the output result of Typeof [] is Object, which cannot meet the requirements. [].constructor === Array //true

2.4 the toString

Object. The prototype. ToString. Call () an Object to belong to what kind of built-in types. Is the most rigorous and general method for determining data types.

  • Judge the base type
Object.prototype.toString.call(null); // "[object Null]"
Object.prototype.toString.call(undefined); // "[object Undefined]"
Object.prototype.toString.call(true);// "[object Boolean]"
Object.prototype.toString.call(123);// "[object Number]"
Object. Prototype. ToString. Call (LNP);// "[object String]"
Copy the code
  • Determine the native reference type
// Function type
Function Beauty(){console.log "(" beautiful LNP); }Object.prototype.toString.call(Beauty);/ / "[object Function]"
Copy the code
// Date type
var date = new Date(a);Object.prototype.toString.call(date);/ / "[object Date]"
Copy the code
// Array type
var arr = [1.2.3];
Object.prototype.toString.call(arr);/ / "[object Array]"
Copy the code
// Regular expressions
var reg = / ^] [\ d {5, 20} $/;
Object.prototype.toString.call(arr);/ / "[object RegExp]"
Copy the code
  • Determine the native JSON object
var isNativeJSON = window.JSON && Object.prototype.toString.call(JSON);
console.log(isNativeJSON);// If the output is "[object JSON]", JSON is native; otherwise, it is not
Copy the code

Q1.

({a:1}).toString() // Return what

({a:1}).__proto__ === Object.prototype
({a:1}).toString() // [object Object]
Copy the code
  • forObjectObject, directly calledtoString()You can return[object Object]. For other objects, you need to passcallTo return the correct type information.

summary

Part 2 Memory

A pile of/stack

The base type is held in stack memory, the value of a reference type is held in heap memory, and the address (pointer) where the value is stored is held in stack memory. This is because data stored in stack memory must be of fixed size, whereas reference types are of variable size.

The difference between heap and stack

Two deep and shallow copies

2.1 Copying data Types

Q1. What does the following code output?

1= =1; [] = = [];/ /?{} = = {};/ /?
Copy the code

A1. Is that right?

1= =1; //true[] = = [];//false{} = = {};//false
Copy the code

A comparison of objects (arrays) is a comparison of references, even if two objects contain the same attributes and the same values.

Basic types of

During replication, a new memory is created in the stack memory to store variable age2. Therefore, the values of variable age and age2 are stored in the stack memory respectively. The changes do not affect each other.

Reference types

When copying, only the Pointers stored in stack memory are copied. The Beauty and Beauty2 Pointers point to the same value in heap memory.

A.x = a = {n:2}

Does that make sense? So here comes the question! Are you ready? Look at the following snippet of code… .

var a = {n:1}; 
var b = a; 
a.x = a = {n:2} 
console.log(a.x); 
console.log(b.x); 
console.log(a); 
console.log(b); 
// What does this code output?
Copy the code

Are you right?

undefined 
{n: 2}
{n: 2}
{n: 1.x: {n: 2}}
Copy the code

parsingLet’s go back to the implementation of this problem. First of all,var a = {n:1}; , a chunk of heap memory is cleared for variable A.

whenvar b = a; , the pointer of variable B points to the same memory space in heap memory as a.

a.x = a = {n:2}Due to “.” Is the highest priority operator, evaluated firsta.x.a.xIt’s not defined yet, so yesundefined.

Assignment operations are then parsed from right to left, executing a = {n:2}, where a (a layer of variables) is reassigned to point to a new memory space.

A.x = A, a.x = A, a.x = A, a.x = A, a.x = A, a.x = A {n:2} is assigned to {n:1 x:undefined}.

At this point, the function completes, so let’s look at (a.x); (b.x); (a); (b); It’s easy to see what they point to.

This question examines the following two knowledge points:

  • The storage and assignment of data of type object on the stack
  • The precedence of an operator in Javascript

Similarly, let’s see if a = a.x = {n:2} is replaced by a = a.x = {n:2}.

var a = {n:1}; 
var b = a; 
a = a.x = {n:2}
console.log(a.x); 
console.log(b.x); 
console.log(a); 
console.log(b);
Copy the code

The answer is the same. Same principle.

2.2 Differences between Deep copy and shallow Copy

  • Shallow copy

Only a pointer to an object is copied, but not the object itself. After copying, the old and new objects point to the same value in heap memory. Modifying the new object changes the old object.

  • Deep copy

When a pointer is copied, it also copies the value to which the pointer points. In other words, an identical copy of the object is created. The new object and the old object are separate memory Spaces.

2.3 Advantages and disadvantages of deep copy and shallow copy, common scenarios

  • Deep-copy benefits

Avoid memory leaks: When copying objects that contain pointer members, the copied object pointer members have their own memory space.

  • Shallow copy benefits

If the object is large and hierarchical, deep copy can cause performance problems. When you encounter scenarios that require deep copy, consider alternatives. In actual application scenarios, shallow copy is more commonly used.

2.4 The method of deep and shallow copy and its disadvantages

Deep copy method:
  • JSON. The parse () with JSON. Stringify ()

For pure JSON data objects, the only objects it can correctly handle are Number, String, Boolean, Array, and flat objects.

let obj = {a: {b:22}};
let copy = JSON.parse(JSON.stringify(obj));
Copy the code
  • postMessage
  • recursive
  • lodash
Shallow copy method:
  • object.assign
  • Extended operators…
  • slice
  • Array.prototype.concat()

2.5 summarize

  • The shallow copy copies only the properties of one layer of objects, while the deep copy copies all layers recursively.

Part three garbage collection

JavaScript has automatic garbage collection, which means that the execution environment is responsible for managing the memory used during code execution.

So, can we just leave it at that? Of course not. Developers just don’t have to pay attention to how memory is allocated and reclaimed, but they still have to avoid doing things that make memory untraceable and reclaimed.

Garbage collection

First, let’s take a look at how JS garbage collection works. In a local scope, local variables are no longer necessary after the function is executed, so their memory can be freed for future use. In this case, the JS garbage collection mechanism is easy to judge and recycle. The garbage collector must keep track of which variables are useful and which are not, and mark unused variables for collection at a later time.

Js garbage collection mechanism has two kinds, one is for tag clearance, one is for reference counting.

So with global variables, it’s hard to tell when it’s no longer needed.

Memory leak vs stack overflow

What are memory leaks and stack overflows, and what is the relationship?

A memory leak is when variables that you no longer access still occupy memory space. A stack overflow is when there are too many calls-on-stack operations and not enough returns on-stack operations. Relationship: The accumulation of memory leaks eventually causes a stack overflow.

What problems can memory leaks cause?

Slow running, crashes, high latency

Four common memory leak traps

  1. Unexpected global variables. These are not recycled variables, especially those used to temporarily store large amounts of information (unless null is set or reassigned)
  2. Timer not destroyed
  3. Node references outside the DOM
  4. Closures (local variables of closures are always kept in memory)

There are two common stack overflows

  1. recursive
  2. An infinite loop

Memory leak avoidance policy

  1. Reduce unnecessary global variables, or objects with long life cycles, and timely dereference (set global objects that are no longer used, global object properties to NULL)
  2. Pay attention to program logic and avoid “endless loops” and the like
  3. Avoid creating too many objects
  4. Reduce hierarchical references

At the end

If there is a mistake in the article, but also hope you big guy correct, thank you.

Go to the online diagnosis and treatment platform of Wedoctor Internet hospital, make a quick consultation, and find a top three doctor for you in 3 minutes.