(1) Pre-knowledge

(1) Some words

-Dan: And actual markup up to date on the ceiling, streak destructure, dob dar imd pixel ratio. // window. DevicePixelRatio devicePixelRatio ellipsis // margin-collapse: -Chuck: Anonymous // Anonymous composition protocol permanent temporary grammarCopy the code

(2) React

(1) the diff algorithm

  • The complexity of traditional algorithms O(n^3), where n is the number of nodes
  • diffThe algorithm can reduce the complexity toO(n)
  • Type:tree diff component diff element-diff

1. tree diff

  • Movement across hierarchies is minimal and negligible
  • Key words:
    • If there is no comparison layer by layer, the whole different tree will be deleted, and the comparison will not be made downward. You only need to traverse the whole tree once to complete the comparison
  • The diff process:
    • Nodes at the same level are compared layer by layer
    • React uses updateDepth to update the depth of the Virtual DOM tree
    • rightThe treeforTo compareTwo trees are only rightNodes at the same levelCompare if theNode does not exist,The node and its children are completely deleted.No further comparison
    • You just iterateAt a time, can complete the comparison of the whole tree
    • First create, then delete
  • What if I move across hierarchies?
    • Diff only considers (same-level node position changes), if transhierarchical, only (create) and (delete) node operations
  • To optimize the:
    • So in development, try to avoid moving components across hierarchies, create and delete directly consume performance,
    • You can hide or show nodes via CSS without actually removing or adding DOM nodes (in case of frequent switching)

2. component diff

  • The diff process:
    • Components of the same type are compared layer by layer according to the original policy
    • Components of different types are judged to be dirty and all nodes of the entire component are replaced
    • For a component of the same type, if the Virtual DOM of the component is not changed (props,state is not changed), there is no need to compare layer by layer. In this case, shouldComponentUpdate() returns false to optimize the performance. No more layer by layer comparisons
    • It is the same type if the class name (component name) is the same

3. element diff

  • When nodes are at the same level, diff will have three operations:Insert INSERT_MARKUP.Delete REMOVE_NODE.Mobile MOVE_EXISTING
  • Some concepts of movement operations
    • OldIndex: Position of the element in the old collection
    • LastIndex: Takes the larger value of oldIndex and the previous lastIndex, which starts at 0, similar to the concept of a cursor
    • Move: oldIndex < lastIndex moves to the position corresponding to lastIndex in the table below
    • Not moved: oldIndex > lastIndex not moved
  • Is a
    • ——— The old and new sets have the same nodes but different locations ———
    • The diff process
    • 1. Check whether (elements in the new set) exist in (old set) one by one with (unique key)
    • 2. If yes, the operation will be performed. The specific (movement rule) is as follows

The first step:

  • Chemical element: B
  • B’s position in the old set:oldIndex = 1
  • B the cursor for the comparison, which defaults to 0 at the beginning:lastIndex = 0
  • Comparison:OldIndex > lastIndex does not move
  • Cursor update before next round of comparison: take the maximum oldIndex=1 and lastIndex=0lastIndex = 1

The second step:

  • Elements: A
  • A’s position in the old set:oldIndex = 0
  • A cursor for comparison:lastIndex = 1
  • Comparison:OldIndex < lastIndex moves
  • Position A moved to:Move to the position of the element A in the new set
  • Cursor update before next round of comparison: take the maximum oldIndex=0 and lastIndex=1lastIndex = 1

Step 3:

  • Chemical element: D
  • Position of D in the old set:oldIndex = 3
  • D cursor for comparison:lastIndex = 1
  • Comparison:OldIndex > maxIndex does not move
  • Cursor update for the next round of comparison: take the maximum oldIndex=3 and lastIndex=1lastIndex = 3

Step 4:

  • Elements: C
  • Position of C in the old set:oldIndex = 2
  • C Cursor for comparison:lastIndex = 3
  • Comparison:OldIndex < lastIndex moves
  • C moved to position:Moves to the position corresponding to the position of element C in the new set
  • Cursor update before next round of comparison: take the maximum oldIndex=2 and lastIndex=3lastIndex = 3

Case 2

  • ——— The new collection has the newly added node, and the old collection has the deleted node ———
  • The diff process



The first step:

  • Element B, oldIndex=1, lastIndex=0, oldInex>lastIndex does not move, updated lastIndex=1

The second step:

  • Element E
  • Decide whether it’s a new, delete, or move operation
  • New:E exists in the new set, E does not exist in the old set, new E
  • New position: position corresponding to the position of E element in the new set,The new E
  • Cursor update before next round of comparison:lastIndex = 1

Step 3:

  • Element C, oldIndex=2, lastIndex=1, oldIndex>lastIndex does not move, the updated lastIndex=2

Step 4:

  • Elements of A
  • Position of A in the set:oldIndex=0
  • A cursor for comparison:lastIndex=2
  • Comparison:OldIndex < lastIndex moves
  • The position moved to is:The position of the element A in the new set
  • Cursor update before next round of comparison:lasIndex = 2

Step 5:

  • Elements of D
  • It doesn’t exist in the new set, it exists in the old set, delete operation, delete D directly

Diff algorithm summary

  • The traditional O(n^3) complexity is reduced to O(n), where n represents the number of nodes
  • There aretreeDiff componentDiff elementDiff
  • treeDiffThere is very little movement across the hierarchy, layer by layer comparison
  • componentDiffShouldComponentUpdate to determine whether components are of the same type, distinguish dirty components and layer by layer comparisons, and VitureDOM is still the same
  • elementDiffFocus on understanding the algorithmic rules of movement
  • A special case:
    • When the first and last elements are swapped, oldIndex is the maximum in the set, which causes nothing to move except the first element, followed by oldIndex< the maximum lastIndex, which causes all elements to move except the first element

(3) JS part

(1) Variable promotion

  • Priority: function parameters > function declaration > variable declaration
  • If the function name already exists, the new one overwrites the old one
  • The variable name already exists, so the declaration of the variable is skipped
------ function a(name, Age) {console.log(name) console.log(age) var name = 'zhang' console.log(name)} a('wang')  function a(name, age) { var name = 'wang'; Var age = unpay; // var name = undefined; // 1. The variables are promoted, but the order is: function parameters > function declaration > variable declaration // 2. Log (name) // 'wang' console.log(age) // undefined; Name = 'zhang' console.log(name) // 'zhang'} a('wang')Copy the code
Function parameter, function name, ------ function b(name) {console.log(name) var name = 'zhang' function name() {console.log('function')} Console. log(name)} b('wang') {function b(name) {var name = 'wang'; Var name = undefined; Function name() {function name() {function name() {function name() {function name(); New override old console.log('function')} console.log(name) // function name() {... } name = 'zhang' console.log(name) // 'zhang' } b('wang')Copy the code

(2) Reflect

  • The purpose of the Reflect object’s design
    • Reflect puts some methods on Object that are obviously internal to the language
    • Modify the results returned by methods on some Object objects to make them more reasonable
  • Reflect has (13) static methods
  • Reflect.has(obj, name)
    • Reflect.hasThe correspondinginThe operator
Reflect.has(obj, name)

---------------------
const obj = {
  name: 'woow_wu7'
}
const has = Reflect.has(obj, 'name')
const notHas = Reflect.has(obj, 'age')
console.log(has, notHas) // true false
Copy the code
  • Reflect.deleteProperty(obj, name)
    • Reflect.deleteProperty()The correspondingdelete obj.name
  • Reflect.construct(target, args)
    • Reflect. Construct (target, args) corresponds to new target(... args)
    • Note:
      • The second argument to reflect. construct(target, args) is an array
      • Provides a way to call the constructor without using the new command
  • Reflect.getPrototypeOf(obj)
    • Reflect the getPrototypeOf corresponding Object (obj). GetPrototypeOf (obj)
    • The difference between:
      • Reflect.getprototypeof () will return an error if the argument is not an object
      • If the argument is not an Object, object.getProtoTypeof () converts the argument to an Object
  • Reflect.setPrototypeOf(obj, newProto)
    • Reflect.setprototypeof (obj, newProto) corresponds to Object.setprototypeof (obj, newProto)
    • The return value:
      • A Boolean value indicating whether the setting succeeded
      • If its prototype object cannot be set, false is returned
  • Reflect.apply(func, thisArg, args)
    • Reflect the apply (func, thisArg, args) is equal to the Function. The prototype. Apply. Call (func, thisArg, args)
    • Note:
      • In general, if you want to bind a Function of this object, you can write fn. Apply (obj, args), but if a Function defined my own way to apply, you can only write the Function. The prototype. Apply. Call (fn, obj, args), Using the Reflect object simplifies this operation.

(3) The array is out of order

  • Sort method
    • The array sort method, which defaults to sort by dictionary, is converted to a string and sorted by dictionary
    • This variable array has no return value
    • Parameters:
      • You can have no parameters
      • It can also be a function (a custom sort takes a function as an argument) that takes two arguments
        • Returns a value greater than 0, indicating that the first member of the comparison is ranked after the second (a-b>0 indicates ascending order)
        • Returns a value less than 0, indicating that the first member of the comparison precedes the second (a-b<0 indicates descending order)
        • Return value equal to 0, position unchanged
    • Out-of-order applications
      • In a batch
      • Guess you like
      • The winning scheme
Arr.sort (() => math.random () -.5) => math.random () -.5) Math.random() -0.5 ===> 50% probability of greater than or less than 0 // math.random () returns the value of the argument: / / function returns a value greater than 0, the said two members of the comparison, the first row in the second behind / / function returns a value less than zero, said two members of the comparison, the first row in front of the second / / function return value is zero, the said two members of the comparison, position unchanged when / / when the decimal number is 0 points, can be omitted in front of 0Copy the code

(4) Functional programming

(1) Curryization of curry function

  • Definition 1 🙁Curryization of the curry function) is to (A function that takes more than one argument), to accept a (Single parameter), and (Return the function) technology
  • Definition 2: A curryfied function that takes (function A) as an argument, returns (new function) when run, and can process (the remaining arguments of function A)

1. Currification stage I

  • Requirements:Add (1, 2, 3, 4)Converted intocurryAdd(1)(2)(3)(4)
  • Disadvantages:
    • Can only handle fixed 4 parameters, can not handle arbitrary multiple parameters, no scalability
    • Only one parameter can be passed at a time
Requirements: add (1, 2, 3, 4) into curryAdd (1) (2) (3) (4) disadvantages: can only deal with the situation of the four parameters, cannot handle arbitrary multiple parameters, there is no scaling type TAdd < T > = (a: T, b, T, c: T, d: T) => T const add: TAdd<number> = (a, b, c, d) => {return a + b + c + d} // Const curryAdd = (a: number) => { return function (b: number) { return function (c: number) { return function (d: number) { return a + b + c + d } } } } console.log('curryAdd(1)(2)(3)(4)', curryAdd(1)(2)(3)(4))Copy the code

2. Currification stage II

  • Increased demand:
    • Processing (Any number of parameters) additive
    • One pass can be passed (Any number of parameters )
  • Principle:
    • Closures are used to hold variables so that they can remember the last value
    • Collect parameters of the curryAdd function when they exist
    • If the curryAdd parameters do not exist, the parameters are collected and added
  • Disadvantages:
    • After the parameters are collected, one more call without parameters is required to perform the addition operation
  • Points to be optimized:
    • The logic of the addition is separately pulled out and passed in through arguments
Function Curry () {let totalParams: number[] = [] function closure(... rest: number[]): any { if (rest.length) { totalParams = [...totalParams, ...rest] return closure } return totalParams.reduce((total: number, current: number) => total + current) } return closure } const curryAdd = curry() const res = curryAdd(1)(2)(3, 4)() console.log(res) // 10Copy the code

3. Cremation stage 3

  • Pre-knowledge:
    • Function.length and arguments objects
      • length: Function length property: Returns the expected number of arguments (parameters)
      • arguments: contains all arguments (arguments) to the function at run time
      • Memory method: arguments is taken inside functions and only valid at execution time
      • Note: Use (rest arguments) instead of (arguments objects) in ES6 arrow functions
  • Deficiencies in Optimization phase 2:
      1. If curryAdd is called once less: Get the length of the parameter by passing add.length directly to the add function (rather than defining it internally), and call it when the length of the collected parameter is greater than or equal to Add.length
      1. The add function is passed in from the outside
function add(a: number, b: number, c: number, d: number, e: number) { return a + b + c + d + e } function curry(fn: (... args: number[]) => number): any { let totalParams: number[] = [] function closure(... rest: number[]): Any {totalParams = [...totalParams,...rest] If (totalParams.length >= fn.length) {return fn(... totalParams) } else { return closure } } return closure } const curryAdd = curry(add) const res = curryAdd(1, 2)(3)(4, Console. log('res11111:>> ', res); console.log('res11111:>> ', res);Copy the code

4. Currified variant

  • In the third stage of curry’s currification, you need to know the length property of the function, and an error will be reported if the add parameter is not declared and arguments are taken instead
function add(a: number, b: number, c: number, d: number, e: number) { return a + b + c + d + e } function curry(fn: (... Args: number[]) => number): any {// Let totalParams: number[] = [] function closure(... rest: number[]): Any {totalParams = [...totalParams,...rest] return closure} closure. GetSum = () => { Call this function to add and return fn(... totalParams) } return closure } const curryAdd = curry(add) const closure = curryAdd(1, 2)(3)(4, 5, 6) const res = closure.getSum() console.log('res2222:>> ', res);Copy the code

(2) Partial functions

  • Definition: a partial function that sets (one or more arguments) to a function and produces a function that returns a smaller element
function add (a, b) { return a + b } function partial (fn) {... } const addPartial = partial(add, 1) / / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- a part of the fixed parameter 1 const res = addPartial (2) / / 3 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- - only 2 part parametersCopy the code

1. Implementation method of partial function 1

  • usebindMethod to implement
    • The bind method
      • Can accept (some or all arguments) of the bound function (fn)
      • Returns a (new function) that can continue (taking the remaining arguments)
function add(a: number, b: number, c: number, d: number): number { return a + b + c + d } function partial(... Rest: any[]): any {const add = rest.shift() // shift, delete first member of array, return add.bind(null,... Rest) // Bind, bind context, returns a new function, } const bindResFn = partial(add, 1,2) const res = bindResFn(3,4) Continue to accept the remaining arguments console.log('resPartial :>> ', res);Copy the code

2. Implementation method of partial function ii

function add(a: number, b: number, c: number, d: number): number { return a + b + c + d } function partial(... rest: any[]) { const add = rest.shift() let paramsFixed: Number [] = [...rest] function closure(... number[] = [...rest]) function closure(... rest: Number []) {paramsFixed = [...paramsFixed,...rest] if (paramsFixed. Length < add.length) {// Closure can be used for closure. Return closure} return add(...) return closure} Return add(... paramsFixed) } return closure } const closure = partial(add, 1, 2) const res = closure(3, 4) console.log('resPratial5 :>> ', res);Copy the code

(3) Memorize

  • Definition: Function memory is a function that caches the result of the last call and returns the same value the next time it is called.
  • Implementation principle:
    • Will (parameter) and (Corresponding resultKeep inobject), when called again, determine whether the object key exists, there is a return cache value
    • Note:
      • Function memorization only makes sense when the function has a return value, because if the parameters are the same, the final result is reused directly, and the result is a return value
      • Multiple parameters can be used at a time. Therefore, when a parameter is used as a key, you need to convert the parameter to a string
      • Closures can be used to store the key and value of each change into an object
  • Pre-knowledge:
    • In operator 🙁The in operator.You can check if an object contains a property, including (Its properties) and (Inherit the attributes )
function add(a: number, b: number, c: number, d: number): number { return a + b + c + d } function memorizeCreator(fn: (... params: any[]) => any) { const cacheMap = {} function closure(... Rest: any[]) {const key = json.stringify (rest) // There may be more than one argument at a time, converted to a string as key if (! cacheMap.hasOwnProperty(key)) { cacheMap[key] = fn(... Rest) // Key does not exist, add mapping console.log(' executed '); } return memorize = memorizeCreator(add) const res1 = memorize(1, 2, 3, 4) const res2 = memorize(1, 2, 3, 4) // call twice, 'executed string printed only once' console.log(res1, res2);Copy the code

(4) Recursive function

1. The tail calls

  • Definition: When the last step in the execution of a function is (to return a call to another function), it is called a tail call
  • advantages:
    • When the inner function executes, the outer function has finished executing and is out of the call stack without causing a memory leak
    • In recursion, tail calls cause only one function to run in the stack without causing performance problems
  • Pay attention to the point:
    • Tail-call optimization only works in strict mode
Tail call: The last step in the execution of a function, which returns a call to another function. When the inner function is called, the outer function has been executed and removed from the stack without causing a memory leak. F (x) {return g(x)} // Tail calls do not cause performance problems because f(x) {return g(x) + 1} // non-tail calls, f(x) {return g(x) + 1} Const a = x => x const a = x => x const a = x => x const a = x => x const a = x => x const a = x => x f() : g(); / / f () and g () is the tail call const a = = > f () () | | g / / f () () the end the call, and then judge const a = = > f () () () && g; // f() is not a tail callCopy the code

2. Recursive functions (tail-recursive optimization)

  • The conditions that constitute recursion
    • The boundary conditions
    • Recursive forward section
    • Recursively return segment
    • When the boundary is not satisfied, recursively advance
    • The recursion returns when the boundary condition is satisfied
  • Tail recursion
Recursive: factorial. Factorial (example 1) Implement a factorial function function factorial(num) {if (num === 1) {return 1} return num * factorial(num - 1) // } const res = factorial(3) console.log(res, 'res') // 6 3 * factorial(2) second time: 3 * 2 * 1 Each time a recursive function is returned, a closure is created. 2. Maintaining multiple execution context stacks is expensive and causes memory leaks. Optimization method: Call (-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- optimization -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --) (case 1 optimization, Function factorial(num, result) {if (num === 1) {return result} return factorial(num-1, result * num)} Use tail recursion to optimize, so that only one function is always executed in the call stack, and no memory runs out, improving performance principle: Factorial (number, result) - 1. The first argument of factorial(number, result) is the number of each calculation and the second argument is the result of each calculation.  - 1. factorial(3, 1) => factorial(2, 1 * 3) - 2. factorial(2, 3) => factorial(1, 1 * 3 * 2) - (3) 6 (-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- to optimize the -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -) (and optimization: Function factorial(res, n) {if (n === 1) return res; return factorial(n * res, n - 1) } function curring(fn) { let par_arr = Array.prototype.slice.call(arguments, 1) const closure = function () { par_arr = par_arr.concat(Array.prototype.slice.call(arguments)) console.log(par_arr, 'par_arr') if (par_arr.length < fn.length) { return closure } return fn.apply(null, par_arr) } return closure } const curringFactorial = curring(factorial, 1) const res = curringFactorial(4) console.log(res)Copy the code

(5) Composition function combination – compose function

  • For example, the compose function is available in the Redux source code
  • Compose function in redux source code – my gold-digging blog
  • Pre-knowledge:
    • The reduce function
      • Each member of the array is processed in turn, eventually accumulating to a value
  • Compose in Redux is already pretty good
  • The compose function in ————— redux —————
    • Function signature:(... funcs) => funcs.reduce((a, b) => (... args) => a(b(... args)))
    • The return value:
      • The end of the compose function (The return value) is a (function), such a function ((... args) => a(b(... args)) )
      • becauseCompose returns: funcs.reduce()And the return value of the reduce function is(... args) => a(b(... args))
  • How to call
    • compose(a, b, c)(1)
    • Compose is a higher-order function that returns a function that also accepts parameters
Redux: compose function compose(... Funcs) {if (funcs. Length = = = 0) {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- (1) if there is no incoming parameters compose function, it returns a function, Return arg => arg} if (funcs.length === 1) {// ------------- (2) Then returned directly the function return funcs [0]} / / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- (3) when the compose of the parameters is greater than 1, return an iterator reduce, Reduce ((a, b) => (... args) => a(b(... args))) } const a = (num) => num + 1; const b = (num) => num + 2; const c = (num) => num + 3; Const resFn = compose(a, B, c)(1) console.log(resFn, 'resFn') compose (1) If the compose function passes in no arguments, return a function that returns the parameters directly. (2) If the compose function passes in one argument, return the function directly. (3) If the compose function passes in one argument, return the iterator reduce. Reduce returns a function - compose(a, C, c) - in this example, the compose function passes in two layers of parameters - the first layer: three functions are passed in as parameters, namely a, B, and c - the second layer: parameter 1 The first layer function is called compose (a, b, c) [a, b, c]. Reduce ((a, b) = > (... args) => a(b(... Args))) step 2: -reduce first iteration - (... args) => a(b(... args)) - b(... Args) execution results as arguments to A => a((... args) + 2) - a((... Args) + 2) Execution result => (... The total return value of args + 2 + 1-reduce => (... args) => (... Args) + 2 + 1 Step 3: -reduce second iteration - (... Args) => ab iteration results (c(... args)) - c(... Args) executes the result as an argument to the result of ab iteration => ((... args) + 3) => (... args) + 2 + 1 - ab((... Args) + 3) Execution result => (... Args) + 3 + 2 + 1-reduce total return value => (... args) => (... Composex = (args) + 3 + 2 + 1 - composex = (... args) => (... Compose (a, B,c) returns the function in the call (1) -composex (1) - returns the value 1+3+2+ 1-7Copy the code
Function composeGenerator(a, b) {// compose Return function(params) {// compose function return a(b(params))}} function reverse(STR) {// reverse array return Str.reverse ()} function transformToString(arr) {return arr.join(")} const arr = [1,2,3,4] const compose = composeGenerator(transformToString, reverse) const res = compose(arr) console.log(res, typeof res, ' Invert array to string ')Copy the code


(5) handwriting function

(1) Call function simulation

  • The call function
    • 1. Bind the this pointer inside the function
    • 2. Call the function in the specified scope
  • Arguments to the call function
    • Theoretically it should be one: object
    • If the argument passed is (Null undefined empty), which is equivalent to passing in the global object (window/global )
    • If the argument passed is (The original value) will be converted to the corresponding (Packaging object )
    • You can take multiple arguments, the first being the object to which this is bound, followed by the arguments needed for the function call to be bound
  • Application of the Call method
    • Occurs when an object is called (inherited property) and the object has a (same name property)
    • The Call method can place the original definition of an inherited method on the object so that it is not affected whether or not the object has a property with the same name
Call method - call method is applied to solve their own attributes override properties on the prototype chain call -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the var obj = {}; Obj. HasOwnProperty ('toString') // false, note that toString is an inherited method, and the empty object does not have that method. Obj. HasOwnProperty = function () {return true; }; Obj. HasOwnProperty ('toString') // true // true Can use the call method to solve the Object. The prototype. HasOwnProperty. Call obj, 'the toString () / / false code above, the hasOwnProperty is obj Object inheritance method, if this method once covered, I'm not going to get the right answer. - The call method solves this problem - it executes the original definition of the hasOwnProperty method on an OBJ object, so that it does not affect the result whether there is a method with the same name on obJ.Copy the code

1. Simulation implementation of call method – ES5

const obj = { name: 'woow_wu7', age: 20, } function add(address, sex) { return this.name + this.age + address + sex } Function.prototype._call = function (obj) { obj = obj || window // Obj = obj? Obj: Window // If the fn.call() argument is (null), Const params = [] const params = [] // params is used to collect arguments to the bind function. For (let I = 1; i < arguments.length; I++) {params. Push (' the arguments [' + I + '] ')} / / note: The loop starts at 1, since arguments[0] is the object of fn's this binding, here is the collection of arguments passed to fn. // Arguments is an array-like object, Argument [2]] // + obj. Fn = this // this is called to specify that the _call method is called by the function. Const res = eval('obj.fn(' + params + ')'); // Const res = eval('obj.fn(' + params + ')'); // Const res = eval('obj.fn(' + params + ')'); There are (add) and (connect) // because: When there + operator command object (objects) into first (original types of values), namely first perform the valueOf - > object itself - > toStirng - > out of the object, are the objects of type string form / / so: ['arguments[1], arguments[2]'] => 'arguments[1], arguments[2]' // [1, 2, 3, '4']. ToString () - > "1, 2, 3, 4" - > returns a string representation of array an array / / in the end: Eval ('obj.fn(argument[1], arguments[2]')) // return value: fn(argument[1], arguments[2]') Delete context.fn // Delete the function on the object // Note: Return res // fn may have a return value, } const res = add._call(obj, 'chongqing', 'man') console.log(res)Copy the code

2. Simulation implementation of Call method – ES6

-es6 const obj = {name: 'woow_wu7', age: 18 } function fn(address, sex) { return this.name + this.age + sex + address } Function.prototype._call = function(context) { context = context ? context : window; context.fn = this; const res = context.fn(... [...arguments].slice(1)); Reflect.deleteProperty(context, 'fn') //delete context.fn; return res; } const res = fn._call(obj, 'chongqing', 'man') console.log(res, 'res')Copy the code

(2) Simulated implementation of apply function

const obj = { name: 'wang', }; function fn(name) { return { name: name || this.name } } Function.prototype._apply = function (context, arr) { context = context ? context : window; context.fn = this; let res = null; if (! Fn res = context.fn()} else {arr instanceof Array? res = context.fn(... Arr) : console.log(' the second argument must be an array ')} delete context.fn; return res; } const result = fn._apply(obj, ['woow_wu7']); console.log(result)Copy the code

(3) Bind simulation implementation

  • The bind method does the following:
    • The binding is referred to by this of the binding function
    • Returns a new function
  • Arguments to bind
    • First argument: the object to which this needs to be bound in the function
    • Second argument: the argument passed to the bound function
      • When you bind, you can pass in some arguments
      • The remaining arguments are passed in when the new function returned after the bind call is called
  • Note:
    • When a second argument is passed to bind (null, undefined, null) in addition to the first argument, it is equivalent to passing the global object (widnow/global).
    • The bind function can be called with some or all of the arguments passed in. Some arguments can be passed in, and the rest can be passed in when the bind return function is called
    • Returns a new function
      • However, called with the new command, the returned function can be used as a constructor, in this case
        • The bind bind this fails because in the constructor, this executes the instance
        • But the parameter passed in is valid
  • keywords
    • Parasitic inheritance. – My gold digger blog
    • The principle of instanceof
    • The apply method
    • closure
  • My nuggets blog – Bind simulation implementation
The bind method of analog implementation -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- const obj = {name: 'woow_wu7, age: 20 } function fn(name, age, address, {this.name = name this.age = age return this.name + this.age + address + sex} fn. Prototype score = 100 The new function returned by _bind, called with the (new) command, Then the generated instances can inherit the fn. The properties and methods on the prototype Function. The prototype. _bind = Function (context) {context = context | | window; // when _bind is passed in: Window /global const self = this; // Bind this to the outer function. In this case, this in _bind refers to fn const bindParams = [...arguments].slice(1) Function fbind() {const fbindParams = [...arguments] // Const totalParams = [...bindParams,...fbindParams] // Return self.apply(this instanceof self? this : Context, totalParams) // (1) If the function fbind returned by _bind is called with the new command // - then this refers to the instance generated by the new function of _bind. So this instanceof self is true // why this instanceof self is true // - Because: Prototype => new TempFn() => TempFn. Prototype => self. Prototype // (2) If the function fbind returned by _bind is not called with the new command, then this in fn needs to be bound to the object context passed in. } TempFn. Prototype = self.prototype; // If (the prototype property of the right constructor is on the prototype chain)} TempFn. Prototype = self.prototype Fbind. Prototype = new TempFn(); fbind. Prototype = new TempFn(); And TempFn. Prototype properties and methods, Return fbind} const fbind = f._bind (obj, 'wang', 20, 'chongqing') const res = new fBind('man') console.log(res, 'res')Copy the code

(4) write a new

  • The new function does:
    • Execute constructor
    • Return instance object
    • The new command itself can execute the constructor, sonew Constructor()new ConstructorCan be
    • If the constructor (forgetting to use new) is called, then (constructor) corresponds to (normal function), and (this) refers to the global object (window/global).
    • How to solve the problem of forgetting to call new?
        1. Use strict mode
        1. To use (This instanceof the constructor), if false is returned, the new call is not passed;The same method was used to simulate the bind method
  • In the ES6Reflect.construct(target, args)
    • Args is an array
    • Reflect.construct(target, args) === new target(... args)
  • The return value of the constructor:
    • Return is followed by an object, which is returned by the new command.
    • Return is not followed by an object, it is followed by a value of the primitive type. The new command returns (this object).
    • If a normal function is called with new, it returns an (empty object)
    • That is:The new command always returns an object, whether in a constructor or a normal function
  • Inheritance correlation
    • Properties and methods in constructors are generated directly on instances that are not shared, resulting in a waste of resources
    • Instances can inherit properties and methods from constructive.prototype, and multiple instances can share them, with modifications affecting each other
  • arguments
    • The advantage of using argumetns is to obtain any number of argumetns when the number of arguments is uncertain
    • In ES6, rest arguments are used to get the rest arguments instead of arguments
  • Principle of the new command
    • Create an empty object
    • By pointing the implicit prototype of an empty object to the constructor’s display prototype, the empty object can inherit properties and methods on constructor Prototype
      • Note:It's best not to use {}.__proto__ = constructive.prototype here
      • Because:__proto__ is only available in browsers
      • Instead of:const obj = Object.create(Constructor.prototype)
    • Point this in the constructor to an empty object
    • Execute constructor
function _new(Constructor, ... // (1) const obj = {} create an empty object // (2) obj.__proto__ = Constructor. Prototype Points the implicit prototype of the empty object to the display prototype of the Constructor, Constructor. Prototype const obj = object.create (Constructor. Prototype) Const obj = object.create (constructive.prototype) const obj = object.create (constructive.prototype) Object. Create (prototypeObj) generates (instance Object) from (parameter Object), Const res = constructive. apply(obj, Rest) // (3) points this in the Constructor Constructor to the empty object // (4) Executes the Constructor Constructor // implements (3)(4) with the apply method // uses REST in ES6 Return (typeof res === 'object' &&res! == null) ? res : The obj // constructor may have a return value of // (5) : if a return is followed by an object, that object is returned; otherwise, this object is returned: obj // typeof } function Constructor(name, age) {this.name = name this.age = age In a constructor, as long as the object is not return, } const res = _new(Constructor, 'woow_wu7', 20) console.log(res, const res = _new(Constructor, 'woow_wu7', 20) console.log(res, 'res') const res2 = new Constructor('woow_wu8', 30) console.log('res2', res2)Copy the code
  • New command simulation implementation, the previous digging summary
Comparing the summary writing method in my previous notes, there are still imperfect places before ah, the summary is as follows: <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, <title>Document</title> </head> <body> <script> function Constructor(name, Constructor) Age) {this.name = name this.age = age return this} function _new() {const obj = { = new Object () const paramsConstructor = Array. The prototype. The shift. The call (the arguments) / / will be the arguments into an Array, and take the first element in the divisor group, ([]).prototype.shift.call(arguments) // = ([]).shift.call(arguments) => Because the Array instance is inherited Array. The properties and methods on the prototype / / is equal to the Array. The prototype. The shift. The apply (the arguments) = > call and apply can / / note: // Push unshift pop Shift will change the array // push unshift return value is after operation, / / pop shift the return value is the length of the array. Add or remove elements obj __proto__ = paramsConstructor. Prototype / / / / the second step will be (implicit stereotype of empty object) to (shows the prototype of the constructor) / / so empty object can inherit the constructor the properties and methods on the prototype / / note: / / const obj = {} and obj __proto__ = paramsConstructor. Prototype / / can be abbreviated to: Const obj = Object. The create (paramsConstructor. Prototype) / / b = Object. The create action (a) is a parameter Object as the prototype, a Const res = paramsconstructive. apply(obj, arguments) // Step 3 // Bind this from the constructor to the empty object and execute the constructor // Note: // argumets (constructor, p1, p2,...); // Argumets (constructor, p1, p2,...); return /Object|Function/.test(Object.prototype.toString.call(res)) ? res : Obj // If the constructor returns an object, the object is returned. // If the constructor returns a primitive type, this is returned. } const instance = _new(Constructor, 'woow_wu7', 20) console.log(instance, 'instance') </script> </body> </ HTML >Copy the code

(6) Regular expression

  • regular expression
  • Rules of regular:
  • Expression:

(1) Two methods of creating regular expressions

  • literalvar regex = /xyz/; (Created at compile time)
  • RegExp constructor:var regex = new RegExp('xyz'); (Created at run time)
  • Advantages of creating a literal re: It’s intuitive and efficient because it’s built at compile time rather than run time

(2) new RegExp(‘abc’, ‘i’)

  • Second argument to the (RegExp) constructor: represents (modifier)
  • new RegExp('abc', 'i') === /abc/i
  • The modifier
    • G: represents global matching, matching all qualified results, mainly used for (search) and (replace)
    • I: ignorecase
    • M: Multiply means multiple lines.

(3) Matching rules

(1) Literal characters and metacharacters

  • Literal characters: Characters in regular expressions represent their literal meaning
  • Metacharacters: do not represent their literal meaning

(2) characters

  • Some character (.) : match divideA carriage return \ r Newline \ n Line separator \u2028 Segment delimiter \u2029All characters other than
  • Position character (^ $) : indicates the beginning and end positions of the string
  • Selector (|(Or, or, or, or

(3) the escape character

  • For (when a metacharacter with special meaning matches itself), it is preceded by (backslash \)
  • The metacharacters that need to be escaped with backslashes have a total of (12Metacharacters
    • . ^ $|? * + () [{\\

(4) Special characters

A carriage return \ r -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- - enter a newline \ n -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the return tabs \ t -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- vertical tabs TAB \ v form-feed character matching \ \ 0 f the null characterCopy the code

(5) character classes[]

  • Take off a character ((^)) : matches characters other than those in the character class
    • [^] : matches all characters
    • . : matches all characters except \n \r \u2028 \u2029
  • Hyphen ([-]) : Short form of sequential characters
    • [1-31] : indicates 1-3, not 1-31
    • Don’t overuse the hyphen; set a wide range because unexpected characters may be selected

(6) Repeat class{} )

  • The repeat class represents the exact number of matches of the pattern
{n} -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- said repeated n times {n,} -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- said repeated at least n times {n, m} -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- - repeating not less than n times, no more than m timesCopy the code

(7)? * + )

  • ? : indicates the occurrence of 0 or 1 times, equivalent to {0, 1}
    • : indicates the occurrence of 0 or more times, equivalent to {0,}
    • : indicates one or more occurrences, equivalent to {1,}.
  • Note: The default is the maximum possible match until the next character does not meet the matching rules, known as greedy mode

(8) Predefined patterns

\d matches any number between 0 and 9, equivalent to [0-9]. Digit digit \D matches all characters other than 0-9 and is equivalent to [^0-9]. \w matches any letters, digits, and underscores, equivalent to [A-za-z0-9_]. Word word \W A character other than all letters, digits, and underscores, equivalent to [^ A-za-z0-9_]. \s matches Spaces (including newlines, tabs, Spaces, etc.) and is equal to [\t\r\n\v\f]. \S matches non-space characters and is equivalent to [^ \t\r\n\v\f]. \b Match word boundary. \B Matches non-word boundaries, that is, inside words. A boundary boundaryCopy the code

(9) Greed model

  • Definition: three quantifiers, each of which is the most likely to match until the next character does not meet the matching rule. This is called greedy mode.
  • How to change greedy mode to non greedy mode ????
    • Add a question mark after the quantifier
Non-greedy mode +? *? Note: No?? Because the? It's bound by itself, zero or oneCopy the code

(1) set of matching

  • Parentheses :(parentheses) in regular expressions to indicate (grouping matches)
  • Patterns in parentheses :(patterns in parentheses) can be used to match (grouped content)
  • Reference matching parentheses: Reference matching parentheses by \n
  • Non-capture group :(? :x)
  • Prior assertion: x(? =y) => x matches only before y, and y is not counted in the return result
  • Antecedent negative assertion: x(? ! Y) => x matches only if x is not in front of y, and y is not counted in the return result
  • Note: When matching groups, do not use the /g global match modifier, otherwise the match function will not match the contents of the group
Reference parenthes-matched content /(.) b(.) \1b\2/.test("abcabc") // true \1 indicates the contents of the first parenthesis matched a \2 indicates the contents of the second parenthesis matched bCopy the code
Var m = 'ABC '. Match (/(? :) b(.) /); M // [" ABC ", "c"] [" ABC ", "c"] [" ABC ", "c"] [" ABC ", "c"] [" ABC ", "c"] [" ABC ", "c"] [" ABC ", "c"Copy the code

(11) Can use regular expression string method

  • match
  • search
  • replace
  • split
(1) match - 1. Return an array (array) - 2. Match (failed) returns (null) -2. One-time return (all the result of the match) (' abcabc.) the match (a/a/g) / / / 'a', 'a' - (2) the replace STR. Replace (search, Replacement) -parameter -search regular expression, representing the search mode -replace the content to be replaced, note that the $dollar symbol can be used, To refer to the content of the replaced by 'aaa'. The replace (' a ', 'b') / / "baa" 'aaa'. The replace (a/a /, 'b') / / "baa" 'aaa'. The replace (/ a/g, 'b') / / "BBB" $&. Matching substring. $' : Matches the text before the result. $' : matches the text after the result. $n: the NTH group of contents to be matched successfully. N is a natural number starting from 1. $$: indicates the dollar sign $. 'hello world'. The replace ()/(\ w +) \ s +) (\ w /, '$2 $1') / / / / "world hello" pay attention to the difference between: /(a)b(c)\1b\2/.test('abcabc') // true 'abc'.replace('b', '[$`-$&-$\']') // "a[a-b-c]c"Copy the code

7. HTTP and HTTPS

(1) TCP/IP protocol – application layer, transport layer, network layer, data link layer

  • Application layer: HTTP FTP TELNET SMTP DNS protocol
  • Transport layer: TCP UDP protocol
  • Network layer: IP protocol ICMP protocol
  • Data link layer
  • The number of words reached the limit, the following article will be summarized


(8) CSS

(1) scrollTop and offsetTop and clientHeight and offsetHeight and scrollHeight

  • scrollTop
    • ScrollTop Indicates the vertical scrolling distance of the scroll bar with a scroll bar
  • offsetTop
    • OffsetTop represents the distance between the top of the current element and the top of the nearest parent element
    • OffsetTop is a fixed value that doesn’t change when scrolling
    • When the element display: None, offsetTop = 0
  • clientHeight
    • Including :(padding)
    • Excluding :(border), (margin), (horizontal scrollbar)
    • For (display:inline), (clientHeight = 0), clientHeight is invalid for inline elements, unit: px, read only
  • offsetHeight
    • Includes :(padding), (border), (horizontal scrollbar)
    • Excluding :(margin)
    • For (display:inline), (clientHeight = 0), clientHeight is invalid for inline elements, unit: px, read only
    • So: offsetHeight = clientHeight + border 2021/10/17 update
  • scrollHeight
    • scrollHeight = scrollTop + clientHeight
    • It only makes sense to talk about scrollHeight with the scrollbar, because scrollHeight===clientHeight without the scrollbar

(2) Ceiling effect

1. CSS scheme – Position: sticky

  • Pre-knowledge:
    • position: fixed absolute relative static inherit sticky
    • Static: the default value
    • Inherit: Inherit the position property from the parent element
    • Sticky: sticky location based on the scrolling position of the user.Equivalent to position:relative + position:fixed
    • Sticky: corresponds to position:relative in normal cases. When the page is rolled beyond the target area, it corresponds to position: Fixed will be fixed at the target position
  • position: sticky
    • position: sticky; top:0px;
    • Location:If (position: sticky) is set, the location is based on (the nearest ancestor element with a scroll bar), if no such ancestor element exists, the location is based on (viewPort) element
    • Note: If multiple elements at the same level have the position:sticky attribute set, the top with the same value will be replaced, but the top with different values will not be

2. IntersectionObserver scheme

  • My nuggets article – useIntersectionObserver

3. Js scheme – scrollTop and offsetTop

  • Use scrollTop and offsetTop to determine whether the scroll reached the top of the scroll

    • When scrollTop >= offsetTop, it reaches the top, and when it reaches the top, it displays the same element as the one that needs the top
    • Hidden when scrollTop <= offsetTop
    • You can also dynamically calculate the height of the top element and fill it with a blank div when it leaves the flow of the document
  • Note:

    • OffsetTop is a fixed, unchanging value that is the distance between the nearest ancestor element that has a positional attribute
    • So the parent element is usually set to position:relative
  • About the position: fixed;

    • Typically, positioning is based on viewPort elements
    • When the transform attribute of the ancestor element is non-None, positioning is based on that ancestor element, not the ViewPort
  • [7-react-admin-ts] [7-react-admin-ts]

(3) StickyFooter sticky layout

  • StickyFooter effect definition: When the content is less than one screen, the footer is fixed at the bottom of the content, when the content is more than one screen, the footer is at the bottom of the content

1. Margin and padding

  • Applicability: suitable for known footer height, good compatibility
  • wrap:{content,footer}
  • Content:
    • min-height: 100%; Make sure to fill the screen when there is less than one screen of content
    • Padding-bottom: footer height; Ensure that the footer does not block the content of the content
    • box-sizing: border-box; Make sure height includes content,padding, and border
  • footer:
    • Margin-top: -fooer height; Make sure the footer moves up to the footer height, so it’s at the bottom, because the content is filling the screen and needs to move up

2. The flex layout

  • Applicability: Compared with other methods, sticky-footer can be implemented even when the footer height is unknown
  • container:{content,footer}
  • The container vessel
    • display: flex;
    • flex-direction: column;
    • min-height: 100%;
  • The content item
    • flex: 1; // Indicates the magnification ratio. If there is remaining space, the magnification occupies the remaining space

3. Calc dynamic calculation

  • Applicability: Also only applicable to footer height known
  • wrap:{content, footer}
  • content
    • Calc (wrap height – footer height)
Footer-top: -50px; footer-top: -50px; -height: 100%; Padding-bottom: 50px; This is to prevent the footer from moving up to the bottom of the viewable area, so that the content of the content area is obscured by the footer. < span style = "box-sizing: border-box; color: RGB (50, 50, 50); line-height: 22px; font-size: 14px! Important; word-break: inherit! Important;" 100% - Note that all default styles of padding and margin are clear - code <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Word-wrap: break-word! Important; "> < span style> * {padding: 0; margin: 0; } html, body { height: 100%; } .wrap { height: 100%; } .content { min-height: 100%; Padding-bottom: 60px; Box-sizing: border-box; // Avoid content being overwritten by footer. // width,height includes content,padding,border background: blueViolet; } .footer { margin-top: -60px; // When the content is insufficient and the screen is full, margin-top makes the footer appear at the bottom height: 60px; background: red; } </style> </head> <body> <div class="wrap"> <div class="content"> <div>content <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br></div> <! -- <div>content <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br></div> <div>content <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br></div> --> </div> <div class="footer">footer</div> </div> </body> </html>Copy the code
2. Flex layout <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Word-wrap: break-word! Important; "> < span style> * {padding: 0; margin: 0; } html, body { height: 100%; } .wrap { /* height: 100%; */ min-height: 100%; display: flex; flex-direction: column; } .content { /* min-height: 100%; */ flex: 1; /* padding-bottom: 60px; box-sizing: border-box; */ background: yellow; } .footer { /* margin-top: -60px; */ height: 60px; background: blue; } </style> </head> <body> // set min-height: 100%; // Make content project flex: 1; This will allow the cotent to fill the remaining space of the spindle, i.e., all the height except the footer. 100% <div class="wrap"> <div class="content"> <div>content <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br></div> <div>content <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br></div> <div>content <br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br></div> </div> <div class="footer">footer</div> </div> </body> </html>Copy the code
Method three - calc attributes - Calculate: calculate <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, "> <meta http-equiv=" x-UA-compatible "content="ie=edge"> <title>Document</title> <style> * {margin: 0; padding: 0; }. Content {min-height: calc(100vh-30px) // The argument is an expression, can use + - * /}. Footer {height: 30px; background: black; color: white; } </style> </head> <body> <div class="content"> content <br><br><br><br> content <br><br><br><br> content <br><br><br><br> </div> <div class="footer"> footer </div> </body> </html>Copy the code

(4) visibility:hidden; Display :none The difference between two

  • visibility: hidden; When hidden, it takes up its original position
  • display: none; No longer takes up the original position when hidden
  • Note: They are all in the DOM node, but hidden by CSS, still in the DOM tree

(5) display: Causes and solutions of inline-block gaps

  • Cause: Blank characters exist between labels
  • Set font size to 0 for the parent element, and then set the desired font size for the child element
  • Solution 2: Don’t wrap labels, just fit them together



(6) The CSS draws triangles

  • Triangle: It means triangle
  • Equilateral triangle, right triangle, triangle with border

Draw triangles in the CSS. 1. Set the width and height to 0 and use different colors on the four edges of the border to display four triangles 2. #b is the top triangle - the length of the triangle is twice the length of the border (border-left+border-right) - the height of the triangle is border-bottom. So change the border-bottom to get triangle 4 with different heights. 5. Example <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Initial - scale = 1.0 "> < title > Document < / title > < style >. The triangle {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- triangle, the high div width is set to 0; Width: 0; height: 0; border: 100px solid transparent; // ----------- border-bottom: 100px solid red; border-bottom: 100px solid red; //------------- rectangle {width: 25px; // rectangle {width: 25px; height: 200px; background: blue; } </style> </head> <body> <div class="triangle"></div> <div class="rectangle"></div> </body> </html> 6. Triangle triangle one-right {display: inline-block; width: 0; height: 0; border: 60px solid transparent; border-left: 60px solid rgb(100, 185, 255); Border-bottom: 60px solid RGB (100, 185, 255); } 7. Equilateral triangle- Principle: width of display part = width of transparent part * √3 - √3 ≈ 1.7321. Triangle -two-equal {display: inline-block; width: 0; height: 0; Border: 34.5 px solid transparent; // Border -bottom: 60px solid RGB (100, 185, 255); } triangle-two-equal {display: inline-block;} 8. width: 0; height: 0; Border: 34.5 px solid transparent; // Border-bottom: 60px solid RGB (253, 0, 0); // Border-bottom: 60px solid RGB (253, 0, 0); position: relative; // Use pseudo classes to make borders. The idea is to make two triangles overlap and then overlay them with different sizes and colors &::before {content: "; position: absolute; top: 50%; left: 50%; transform: translate(-51%, -29%); width: 0; height: 0; border: 29px solid transparent; // Border-bottom: 50px solid RGB (100, 185, 255); // Border-bottom: 50px solid RGB (100, 185, 255); }}Copy the code

(7) the progress bar

  • Gradient: the gradient
  • (target.scrollTop/(target.scrollheight-target.clientheight))px;
  • Width of scroll: target.scrollTop
  • Width to scroll: target.scrollTop
  • Github source link

(8) Position: The relationship between fixed and transform

  • position:fixed
    • In general, positioning is based on viewPort elements
    • When an ancestor element has a transform attribute set to non-None, fixed positioning is no longer based on viewPort, but resides in an ancestor element with a transform attribute set to non-None

(9) model of the box

  • (Standard box model) and (IE box model)
  • Box-sizing: content-box; ——– Width and height Include: Content
  • Box-sizing: border-box; ———- Width and height include content, padding, and border

(10) One pixel 1px physical border on the mobile terminal

  • Implement a pixel physical border with (@media), (pseudo-element), (-webkit-min-device-Pixel-ratio), (Transform: scaleY())
  • How to get the screen pixel ratio: window.DevicepixelRatio
  • On the Web, window.devicePixelRatio === 1
  • On mobile devices, window. DevicePixelRatio is 2 or 3
<! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Word-wrap: break-word! Important; "> < span style> * {margin: 0; padding: 0; } .one-px-border { height: 200px; width: 200px; position: relative; }. One - px - border: : before {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- pseudo element, the current element's child elements, not in the DOM, promote efficiency content: "'; / / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- you must set up the content position: absolute; left: 0; bottom: 0; width: 100%; height: 1px; // Height: 1px BACKGROUND: red; } @media screen and (-webkit-min-device-pixel-ratio: 2) {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- than 2 pixels, the scaling of the size of the y direction from 0.5 one - px - border: : before {transform: scaleY. (5); / / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- double screen, the pseudo class y direction to reduce the 0.5 x}} @ media screen and (its - min - device - pixel - thewire: 3) {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- - pixel ratio is 3, the scaling of the size of the y direction from 0.333 one - px - border: : before {transform: scaleY (. 33333); // ----------------------------------------- 3x screen, </style> </head> <body> <div class="one-px-border"></div> </body> </ HTML >Copy the code

(11) @media media query

  • @media Media Query: mainly used for (responsive layout), define different (styles) for different (screen size)
  • Usage: Can be used in (Link tag) and (CSS)
(1) @ @ media media grammar mediaType and | not | only (media feature) {CSS code} 1. MediaType media type - screen: computers, tablets, mobile phones - print: Printer - all: all devices 2. MediaFeature Media characteristics - Each expression of media characteristics must be enclosed in parentheses 3. The logical operator - and - and is used to combine multiple media functions into a single media query - requires each link function to return true for the query to be true // --------------------------- tru for the query to be true - It is also used to combine media functionality with media types. - not - only 4. -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the link tag using the @ media -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- < link rel = "stylesheet" media = "screen and (max-width: 600px)" href="small.css" /> <link rel="stylesheet" media="screen and (min-width:600px) and (max-width:900px)" Href ="style.css" type="text/ CSS "/> When the screen width is larger than 600px and smaller than 900px, Use style. CSS file 5. -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the CSS used in @ media -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- @ mixin bgColor ($bgColor) { .interview-media { .media-main { .media-main__title { background: $bgColor; padding: 10px 0; } } } } @include bgColor($bgColor:#c6fd8f); @media screen and (min-width: 1200px) {// include bgColor($bgColor:#a8c9ff); } @media screen and (min-width: 1000px) and (max-width: @include bgColor($bgColor:#ffa9ff); } @media screen and (max-width: 900px) {// < 900px style @include bgColor($bgColor:#ffc7c7); }Copy the code

(12) em

  • Em is a relative unit
  • When em is used as the unit of font size, 1em indicates the font size of the parent element
  • If em is used as the unit of other attributes, 1em indicates the size of its font size
  • Disadvantages of the EM layout:
    • The downside of em's flexible layout is that it is a matter of timing. If the font size of a node changes, all subsequent elements have to be recalculated
.em { .max-border { font-size: 20px; padding: 10px; background: #fdf2ff; .em__div1 { background: #bbdffd; font-size: 1em; }. Em__div2 {background: #bbfdc9; font-size: 20px; height: 10em; Font-size: 16px; font-size: 16px;Copy the code

Rem layout (13)

  • Rem = 1rem=HTML font size
  • Physical pixels = CSS pixels (device-independent pixels) * pixel ratio (multiple screens)
  • Unit conversion:
    • DeviceWidth/The total width of the UI design text = the actual width of an element/the UI width of that element
    • The actual width of an element = deviceWidth/ the total width of the UI design * the UI width of the element
      • DeviceWidth: can be obtained in JS or CSS mode
        • Js way: (document. DocumentElement. ClientWidth) that is the width of the HTML
        • CSS mode: vw (note: vw includes the width of the scrollbar, so subtract it or disable the scrollbar)
  • Steps for rem layout:
Rem layout step design draft: under the premise of 750px as the benchmark, the overall three steps: 1. Set the HTML font size dynamically (there are two ways to set the HTML font size dynamically: JS or CSS) 2. Font size can be inherited. To avoid setting the HTML font size to affect the subsequent font size, do not set font size 1 and 2 on the body. Dynamically set the font size of the HTML ----------- (can be implemented with JS, Can also use CSS calc method implementation) (1) js document. DocumetElement. Style. FontSize = document. DocumetElement. ClientWidth / 750 + 'p' DesignWidth - X = deviceWidth/750 * designWidth - Final result: x = 1rem * designWidth = designWidth rem (2) css-calc() .html { font-size: calc(100vw / 750); } 3. body body { font-size: 16px; // The browser's default font size is 16px}Copy the code
  • Example 1
import React, { useState } from 'react' import './rem.scss' const Rem = () => { const [links] = useState([ { name: 'Rem - my blog the nuggets' layout, url: "https://juejin.cn/post/6844904090644774926#heading-34"},]) const handleClick = (e: React.MouseEvent) => { document.documentElement.style.setProperty( 'font-size', ` ${document. DocumentElement. ClientWidth / 750} the total width of px ` / / HTML into 750 pieces, } const renderLinks = () => links.map(({name, Url}) = > < div key = {name} > < a href = target = "blank" > {url} {name} < / a > < / div >) return (< div className = "rem" > < / p > < p > rem layout < br /> <h1>!!!! Please open </h1> <div className="max-border"> <div className="rem__test"> <div> Test REM layout </div> <div>width: 200rem</div> <div className="rem__test2"> <div> </div>< /div><br/><br/> <button onClick={handleClick}> Set the HTML font size to: Html. clientWidth /750px width of the design, so that 1rem = 1/750px = width of each element of the design, </button> <br/> <div> {renderLinks()} </div> </div>)} export default RemCopy the code
.rem { .max-border { .rem__test { width: 200rem; height: 200rem; background: rgb(156, 255, 161); } .rem__test2 { width: 100px; height: 100px; background: rgb(192, 188, 255); }}}Copy the code

  • Example 2
    • How do I write px directly to actually have rem units, that is, I still use PX units during development
      • Write a pxtoREM function, transform
      • Leverage third-party dependencies (PostCSS-Pxtorem)
@function px2rem ($px) {@return $px + rem; }. Demo {width: px2rem(100); height: px2rem(100); } (2) postcss-pxtorem https://github.com/cuth/postcss-pxtorem if it is based on the webpack project, Can new postcss. Config. Js file -- -- -- -- -- -- -- -- -- -- -- -- -- - app. Vue -- -- -- -- -- -- -- -- -- -- -- -- -- - * {margin: 0; padding: 0; } html { font-size: calc(100vw / 750); } -- -- -- -- -- -- -- -- -- -- -- -- -- -- - postcss. Config. Js -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- - can also be in vue. Config. Js configuration in the -- -- -- -- -- -- -- -- -- -- -- -- -- -- - the module. Exports = {plugins: {' autoprefixer: {-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- solving browser compatibility of prefix browsers: [' Android > = 4.0 ', 'iOS > = 7']}, 'postcss - pxtorem' : RootValue: 1, // cardinality, i.e. 1px = 1rem unitPrecision: 5, propList: ['*'], selectorBlackList: [], replace: true, mediaQuery: false, minPixelValue: 0, exclude: /node_modules/i } } } --------------- ue.config.js --------------- module.exports = { lintOnSave: true, css: {loaderOptions: {postcss: {plugins: [require('postcss-pxtorem')({rootValue: 1, // convert the base selectorBlackList: [' weui ', 'mu], / / ignore conversion regular match propList: [' *'],]}}}}}),Copy the code

(14) Single-line ellipsis and multi-line ellipsis

  • Ellipsis: ellipsis
  • Direction received:
Single-line ellipsis and multi-line ellipsis <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Initial - scale = 1.0 "> < title > Document < / title > < style >. Content1 {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- ellipsis line background: yellow; width: 200px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }. Content2 {/ / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the multi-line ellipsis background: red; width: 100px; overflow: hidden; display: -webkit-box; // ------------------------------ display: -webkit-box -webkit-box-orient: vertical; / / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- - its direction - line - clamp: 2; / / -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- the number of rows} < / style > < / head > < body > < div class = "content1" > ellipsis ellipsis ellipsis ellipsis ellipsis line line line line line </div> <div class="content2"> Multiple ellipses, multiple ellipses, multiple ellipses, multiple ellipses </div> </body> </ HTML >Copy the code

(15) Block inline inline-block difference

Common inline block elements: INPUT, textarea, select, img (block) Common block-level elements: Div, form, table, P, H1 ~ H6, ul, li, OL, DL, pre; The width of the block element can be set to the width of its parent element. By default, the width of the block element automatically fills the width of its parent element. - Inline elements set width and height to invalid. - Inline elements set margin to invalid in horizontal direction and invalid in vertical direction. - Inline elements set padding to valid for itself. 3. Inline-block - Has both the width and height attributes of a block and the non-line attributes of a line elementCopy the code

(16) Double column layout – fixed on the left and adaptive on the right

  • float
    • Left:width: 100px; float: left;
    • right: If you need to make any Settings
  • Absolute positioning
  • Flex layout
import React, { useState } from 'react' import './layouts.scss' const Layouts = () => { const [links] = useState([ { name: 'Two-column Layout - My Nuggets Blog ', URL: 'https://juejin.cn/post/6844904090644774926#heading-27' }, ]) const renderLinks = () => links.map(({ name, url }) => <div key={name}><a href={url} target="blank">{name}</a></div>) return ( <div className="layouts"> <p> Two-column layout </p><br /> {/* float */} <div className="max-border"> <div className="float-left"></div> <div className="float-right"> <h1>float</h1> <h1>left: width: 100px; </h1> <h1>left: float: left</h1> <h1>right: </h1> </div> </div> {/* absolute */} <div className="max-border"> <div className=" absolt-left "></div> <div ClassName ="absolute-right"> <h1> <h1>left: 100px; </h1> <h1>left: height: 100%; </h1> <h1>right: position: absolute; </h1> <h1>right: left: 100px; </h1> <h1>right: top: 0; right: 0; bottom: 0; </h1> </div> </div> {/* flex */} <div className="max-borderx"> <div className="max-border-inner"> <div className="flex__left"></div> <div className="flex__right"> <h1>flex</h1> <h1>container: display: flex; </h1> <h1>left: flex: 0 0 100px; width: 100px; </h1> <h1>right: flex: 1</h1> </div> </div> </div> <div> {renderLinks()} </div> </div> ) } export default LayoutsCopy the code
.layouts {// float mode.max-border {. Float -left {background: #ff8800; height: 100%; width: 100px; float: left; }. Float -right {// no need to set the right background: #ffefb8; height: 100%; Max-border {position: relative; max-border {position: relative; .absolute-left { background: #ff8800; width: 100px; height: 100%; } .absolute-right { background: #ffefb8; position: absolute; left: 100px; top: 0; right: 0; bottom: 0; } } // flex .max-borderx { width: 360px; height: 360px; display: inline-block; border: 1px solid rgb(201, 201, 201); .max-border-inner { width: 100%; height: 100%; display: flex; .flex__left { background: #ff8800; flex: 0 0 100px; } .flex__right { background: #ffefb8; flex: 1; }}}}Copy the code

(17) Three column layout – Holy Grail layout

  • flex
  • Absolute positioning
  • floating
Holy Grail layout - Flex <! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Word-wrap: break-word! Important; "> < span style> * {margin: 0; padding: 0; } html, body { width: 100%; height: 100%; } .container { width: 100%; height: 100%; display: flex; justify-content: flex-start; align-items: flex-start; } .left { height: 100%; background: red; flex: 0 0 200px; // flex: 0 0 200px; } .center { height: 100%; background: blue; flex: 1; // flex: 1; } .right { height: 100%; background: yellow; flex: 0 0 200px; // flex: 0 0 200px; } </style> </head> <body> <div class="container"> <div class="left">left</div> <div class="center">center</div> <div class="right">right</div> </div> </body> </html>Copy the code
Grail layout - Float <div class="container"> <div class="left"></div> <div class="right"></div> <div class="main"></div> ## main put last  </div> .left { float: left; width: 100px; } .right { width: 200px; float: right; } .main { margin-left: 120px; margin-right: 220px; } ## or trigger the BFC, the BFC area, does not overlap with the floating element. Main {overflow: hidden; }Copy the code

(18) BFC

  • BFC ( Block Formatting Context ) Block level formatting context, is a characteristic
    • A BFC is a rendering area of a page with a set of rendering rules that determine how its children are positioned and how they interact with other elements
    • Elements with BFC element characteristics can be treated as separate elements, and elements in the container do not affect the layout of other elements
  • How do I trigger the BFC feature
    • The root element
    • Floating flot
    • Absolute position: Absolute and fixed
    • Display inline-block, table-cells, flex
    • Overflow values other than visible (hidden, auto, scroll)
  • BFC layout rules
    • Margin folded
      • Margin folding occurs between two adjacent block-level elements belonging to the same BFC
    • Separate container
      • Elements inside the container do not correspond to elements outside the element
  • The use of the landing
    • Remove margin overlap
    • Clear float, resolve float caused by parent element height collapse
  • Use BFC to clear float principle
    • Elements with BFC properties include all child elements (including float elements) when calculating height
    • So it can solve the problem caused by (floating) (parent height collapse)
  • Why clear float
    • Cause: The height of the parent element collapses when the floating element leaves the document flow (when the parent element has no height set)
    • Workaround: Trigger the BFC feature, or use the clear attribute on the siblings of the floating element

(19) Clear the float

  • Clear float method – resolve parent element height collapse

(1) overflow: hidden

  • Method: Set Overflow: Hidden on the floating element’s parent
  • Principle: When BFC is triggered, all child elements including floating elements will be counted when calculating height of elements with BFC characteristics, so height collapse will not occur
  • So: Overflow: hidden Scroll auto works, as long as it's not (overflow: visible)
  • Which attributes can trigger the BFC can be used to clear the float
    • The root element
    • floating
    • Absolute positioning: Absolute fixed
    • Overflow: hidden/auto/scroll
    • display: inline-block/flex/table-cell

(2) Pseudo-element (::before) (::after)

  • Method: Add a dummy element to the parent element of the float element
  • Principle:
    • 1. The pseudo-element is a child of the current element. Set the clear attribute to the pseudo-element. Note that the clear attribute applies only to block-level elements
      • Be careful to distinguish pseudo-elements from pseudo-classes
        • Pseudo-element: is an element ::after ::before
        • Hover :link…
    • 2. Add the pseudo-element to the parent element of the float element, and set clear:both, equivalent to setting the clear attribute to the sibling element of the float element

(3) Insert a child element, such as span, in the float element’s parent, set clear property, display to block

  • In the same way that you add false elements, you use child elements to expand the height of parent elements

(4) Float the parent element of the float element, triggering the BFC

<! DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, Word-wrap: break-word! Important; "> < span style>.father {background: yellow; padding: 30px; position: relative; /* float: left; */ /* position: absolute; */ /* overflow: hidden; */ /* display: inline-block; */ } .father::before { content: '.'; height: 100PX; width: 100PX; position: absolute; top: 0; left: 0; display: block; background: greenyellow; clear: both; } .brother { height: 200px; width: 200px; } .child { height: 200px; width: 200px; background: red; float: left; } </style> </head> <body> <div class="father"> <div class="child">child</div> <div class="brother"></div> </div> </body>  </html>Copy the code

(20) Margin collapse

  • Margin overlap occurs when the margins of two adjacent boxes (parent or brother) combine into a single margin
  • Horizontal margins do not overlap

1. Overlapping rules (under the same BFC)

  • When the (vertical) margin of two adjacent elements is (positive), the overlap value is the (greater) of the two.
  • When the (vertical) margin of two adjacent elements is (negative), the overlap value is (larger absolute value)
  • Margin of two adjacent elements, the overlap value is the sum of the two

2. How to solve the problem of upper and lower margin overlap in the same BFC

  • 1 Two adjacent elements use a margin in the same direction
  • Use padding instead of margin
  • 3 Make the two elements under different BFC
    • The root element
    • Floating: float
    • Absolute position: Position: Absolute fixed
    • display: inline-block, flex, table-cell
    • Unavailable (unavailable: hidden, Scroll, auto)

(21) Multi-column contour layout

  • Float + pading, margin cancels
  • Table – ceil layout
  • Flex layout
Column-equal {// flex mode multiple columns equal height. Max-border-one {. Max-border-flex {display: flex; flex-flow: row nowrap; } & > div { width: 25%; background: #f6ffed; }} // float, float +margin; max-border-two {. Max-border-float {overflow: hidden; & > div { float: left; width: 25%; background: #f6ffed; padding-bottom: 999px; margin-bottom: -999px; }}} // table-ceil layout. Max-border-three {. Max-border-table {display: table; & > div { display: table-cell; width: 25%; background: #f6ffed; }}}}Copy the code

(22) Horizontal and vertical center

  • Table – ceil layout
    • Parent element: display: table-cell;
    • Parent element: text-align: center;
    • Parent element: vertical-align: middle;
    • Child element: display: inline-block;
  • Absolute positioning
    • Parent element: position: relative;
    • Child element: position: absolute;
    • Child element (unknown width and height) : top: 50%; left: 50%; transform: translate(-50%, -50%);
    • Child element (know width and height) : top: 50%; left: 50%; margin: -halfHeight -halfWidth;
  • The grid layout
    • father: display: grid;
    • child: justify-self: center;
    • child: align-self: center
  • Flex layout

Program source code

  • Program source code
  • Online address

data

React – 1 – zhihu diff algorithm (speaks good concept part) zhuanlan.zhihu.com/p/103187276 React – diff algorithm 2 – Jane books (elementDiff speaks good moving parts) www.jianshu.com/p/3ba082201… Css-interview my nuggets article juejin.cn/post/684490… Margin overlapping juejin. Cn/post / 684490… Various drawing methods of triangles juejin.cn/post/684490… Functional programming my nuggets article juejin.cn/post/684490…