ES6总结

1.let和const以及与var区别

1.1  作用域

var:
变量提升(Hoisting):var 声明的变量会被提升到其作用域的顶部,但赋值不会提升。这意味着你可以在声明之前引用该变量(但会得到 undefined)。

  console.log(llb);var llb="123456789";

函数作用域:var 声明的变量在整个函数内都是可访问的,即使它们在代码块(如 if 语句或 for 循环)内声明。
let、const:

块级作用域:块是由 {} 包围的代码块。
没有变量提升:

//如果尝试在声明之前访问 let 变量,会抛出 ReferenceErrorconsole.log(xi);let xi='123456789';

常量:一旦 const 变量被赋值,其值就不能被重新赋值(但如果是对象或数组,其内容可以被修改)。

1.2  重复声明

var:
可以在同一作用域内多次声明同一个变量而不会报错。
let 和 const:
不允许在同一作用域内重复声明同一个变量,否则会抛出 SyntaxError。

1.3  重新赋值

var 和 let:
可以在声明后重新赋值。
const:
必须在声明时初始化,并且之后不能重新赋值(但如果是对象或数组,其内容仍然可以修改)

// let 示例  
if (true) {  let y = 20;  console.log(y); // 输出: 20  
}  
// console.log(y); // 会抛出 ReferenceError,因为 let 有块级作用域  // const 示例  
const z = { value: 30 };  
console.log(z.value); // 输出: 30  
z.value = 40;  
console.log(z.value); // 输出: 40,对象内容可以修改  
// z = {}; // 会抛出 TypeError,因为 const 不能重新赋值

2.解构赋值

一、数组解构赋值

数组解构允许直接从数组中提取值,将它们赋给声明的变量。使用方括号[]包围变量名,并与待解构的数组相对应。

  1. 基本用法
const arr = [1, 2, 3]; 
const [a, b, c] = arr; 
console.log(a); // 输出 1 
console.log(b); // 输出 2 
console.log(c); // 输出 3
  1. 忽略某些值

如果解构的变量数量少于数组中的元素,未指定的元素将被忽略。

const [x, y] = [1, 2, 3, 4]; console.log(x); // 输出 1 console.log(y); // 输出 2
  1. 设置默认值

以防解构的变量在数组中不存在,可以设置默认值。

const [x = 10, y = 20] = [1, 2]; 
console.log(x); // 输出 1 
console.log(y); // 输出 2

注意,如果数组成员的值不严格等于undefined,默认值不生效(null的话相应值依然为null)。

  1. 使用剩余参数

使用剩余参数...rest可以捕获数组中未指定的其余元素。

const [x, y, ...rest] = [1, 2, 3, 4, 5]; 
console.log(x); // 输出 1 
console.log(y); // 输出 2 
console.log(rest); // 输出 [3, 4, 5]

数组套数组的时候,可以使用同样的结构对应原数组,解构出对应的值。

let [a, [b, c, d]] = [1, [3, 4, 5]]; 
console.log(a, b, c, d); // 输出 1, 3, 4, 5

二、对象解构赋值

对象解构允许从对象中提取数据,并将它们赋值给声明的变量,这些变量名需要与对象的属性名相匹配(除非显式指定别名)。使用花括号{}包围变量名和它们对应的属性名。

  1. 基本用法
const obj = { name: 'Alice', age: 25 }; 
const { name, age } = obj; 
console.log(name); // 输出 Alice 
console.log(age); // 输出 25
  1. 设置别名

可以为解构的属性设置别名。

const { name: userName, age: userAge } = obj; 
console.log(userName); // 输出 Alice 
console.log(userAge); // 输出 25
  1. 设置默认值

对象解构赋值同样支持默认值。

const { address = 'Unknown' } = obj; console.log(address); // 输出 Unknown
注意,对象解构中的默认值生效条件是对象属性值严格等于undefined,null不会生效,解构失败值为undefined
  1. 剩余属性

使用剩余参数...可以捕获对象中未指定的其余属性。

const { address = 'Unknown', ...otherInfo } = obj; 
console.log(address); // 输出 Unknown 
console.log(otherInfo); // 输出 { age: 25 }
  1. 嵌套对象解构

对象包含对象的时候,可以通过属性名:{}获取对应的属性值。

let person = { uname: 'zs', age: 34, dog: { name: '汪仔', age: 3 }, cat: { name: '小花', age: 2 } }; let { uname, cat: { name } } = person; console.log(uname, name); // 输出 zs, 小花
  1. 使用表达式

解构赋值中,如果默认值是表达式,表达式惰性求值,只有在用到的时候才会去执行。默认值也可以引用解构赋值的其他变量,但该变量必须已声明。

三、解构赋值的应用场景

  1. 函数参数

解构赋值可以用于函数参数,使函数更加简洁和易于理解。

function fn({ name, age }) { 
console.log(name, age); 
} 
fn({ name: 'Alice', age: 25 }); // 输出 Alice, 25
  1. 遍历数据结构

解构赋值可以用于遍历数组、对象、Map等数据结构。

var map = new Map(); 
map.set('first', 'hello'); 
map.set('second', 'world'); 
for (let [key, value] of map) { 
console.log(key + " is " + value); 
} 
// 输出 first is hello, second is world
  1. 提取JSON数据

在Ajax请求返回数据处理中,可以使用解构赋值提取JSON数据。

const data = { needServicePwd: true, needImgCode: false, needSmsCode: true }; 
({ needServicePwd: this.needServicePwd, needImgCode: this.needImgCode, needSmsCode: this.needSmsCode } = data);

3.模板字符串

一、定义与语法

ES6模板字符串:
使用反引号(`)包裹,而不是传统的单引号(')或双引号(")。
支持在字符串中嵌入表达式,通过${expression}的占位符语法实现。
ES5及之前字符串:
只能使用单引号或双引号包裹。
不支持在字符串中直接嵌入表达式,通常需要通过字符串拼接(使用+操作符)来实现。

二、功能特性

字符串插值:

ES6:支持字符串插值,允许在字符串中嵌入变量或表达式的结果。

          let myname= 'John'; let greeting = `Hello ${myname}, how are you?`;console.log(greeting);

ES5及之前:不支持字符串插值,需要通过字符串拼接来实现。

let name = 'John'; let greeting = 'Hello, ' + name + '!';

多行字符串:

ES6:模板字符串默认支持多行,无需使用特殊的换行符或字符串连接符。

const name = "Alice";  
const age = 30;  
const personalInfo = `姓名: ${name}  
年龄: ${age}  
职业: 开发者`;  
console.log(personalInfo);//输出:姓名: Alice  年龄: 30  职业: 开发者

ES5及之前:不支持多行字符串,需要使用字符串连接符(+)或数组(通过join方法)来创建多行字符串。

嵌套表达式:

ES6:允许在模板字符串的占位符中嵌套更复杂的表达式,包括函数调用、算术运算等。

 let a1 = 5; let b1 = 10;let sum =`The sum of ${a1} and ${b1} is ${a1 + b1}`;

ES5及之前:不支持在字符串中直接嵌套表达式,需要通过字符串拼接和额外的计算来实现。
标签模板:
ES6:支持标签模板(tagged templates),允许在模板字符串前面加上一个标签函数来自定义字符串的处理方式

function greet(name) {  return `你好, ${name}!`;  
}  const user = "Bob";  
const message = `欢迎信息: ${greet(user)}  
今天是个好日子。`;  console.log(message);

ES5及之前:不支持标签模板,无法实现对字符串的自定义处理。
原始字符串:
ES6:通过String.raw方法可以创建原始字符串,即不进行特殊字符的转义处理。这对于处理包含转义字符的字符串特别有用。

let name = 'Alice';
console.log(String.raw`Hello, ${name}!`);

ES5及之前:无法直接创建原始字符串,需要手动处理转义字符。

4.ES6箭头函数

 基本语法

箭头函数使用 => 符号来定义函数。以下是几种常见的用法:

没有参数或只有一个参数:

const sayHello = () => {  console.log("Hello!");  
};  //1)可以省略小括号,当形参只有一个的时候 
const square = x => x * x;

多个参数

const add = (a, b) => a + b;

带有函数体的箭头函数:

如果箭头函数需要包含多条语句,则必须使用花括号 {} 将它们包围起来,并且需要显式地返回结果(使用 return 关键字):

const multiplyAndAdd = (a, b, c) => {  const result = a * b;  return result + c;  
};
特性
1.没有自己的 this:

箭头函数不会创建自己的 this 上下文,它会捕获其所在上下文的 this 值。这意味着在箭头函数内部使用 this,其值来自于箭头函数定义时的上下文,而不是调用时的上下文。

function Person() {  this.age = 0;  setInterval(() => {  this.age++; // `this` 指向 Person 实例  console.log(this.age);  }, 1000);  
}  

const p = new Person();

2.没有 arguments 对象:

箭头函数不提供 arguments 对象。如果需要访问函数的参数列表,可以使用剩余参数(...args)来替代:

const showArguments = (...args) => {  console.log(args);  
};  
showArguments(1, 2, 3); // 输出: [1, 2, 3]
3.不能用作构造函数:

箭头函数不能使用 new 关键字来调用,因为它们没有 [[Construct]] 方法,不能被用作构造函数。

const Foo = () => {};  // 会抛出错误:TypeError: Foo is not a constructor  
const bar = new Foo();
4.没有 prototype 属性:

由于箭头函数不能用作构造函数,因此它们也没有 prototype 属性。

const Foo = () => {};  
console.log(Foo.prototype); // 输出: undefined
5.不支持 yield:

箭头函数不能用作生成器函数(即不能使用 yield 关键字)。

const gen = () => {  yield 1; // 会抛出错误:SyntaxError: Unexpected strict mode reserved word  
};
应用场景

以下是一个更复杂的示例,展示了箭头函数在数组操作中的应用:

const numbers = [1, 2, 3, 4, 5];  
// 使用箭头函数计算数组元素的平方并返回一个新数组  
const squares = numbers.map(x => x * x);    
console.log(squares); // 输出: [1, 4, 9, 16, 25]
//找出大于2的数组const newArr2 = arr.filter(num => num >2);console.log(newArr2);

点击div改变颜色结合定时器(this指向外围作用域的this)

        const box = document.getElementById('box');box.addEventListener('click', function(){setTimeout(() => {this.style.backgroundColor = 'blue';}, 2000);});
注意
  • 箭头函数适合与this无关的问题的回调,定时器,数组的方法的回调
  • 箭头函数不适合与this有关的回调,事件回调,对象的方法

5. ES6允许给函数的参数赋初始值

  • 在 ES6(ECMAScript 2015)中,你可以在函数定义时为参数设置默认值。这使得函数调用时如果未提供某些参数,则会使用默认值。
  • 带默认值的参数必须位于没有默认值的参数之后。如果违反这一规则,会导致语法错误。
        //ES6允许给函数function的参数设置默认值,这样可以简化调用函数的过程const add=(a,b,c=10)=>{
return a + b + c;}console.log(add(1,2));console.log(add(1,2,3));

输出

 

函数赋值与解构赋值相结合

connect({name: 'Jack',age: 25,address: 'New York'
});function connect({name, age, address}){console.log(`My name is ${name}, I am ${age} years old, and I live in ${address}.`);
}

6. ES6扩展运算符(Spread Operator)和剩余参数(Rest Parameters)

ES6中的Rest参数(Rest parameters)是一种语法结构,它允许我们将一个不定数量的参数表示为一个数组

一、语法

Rest参数以三个点(...)开头,后跟一个参数名。这个参数名实际上是一个数组,用于收集函数调用时传入的所有剩余参数。

function myFunction(a, b, ...rest) {  // rest是一个数组,包含所有剩余的参数  console.log(rest);  
}

二、使用场景

处理可变数量的参数:

当函数需要接收任意数量的参数时,可以使用Rest参数来收集所有剩余的参数。

function sum(a, b, ...rest) {  let total = a + b;  for (let i = 0; i < rest.length; i++) {  total += rest[i];  }  return total;  
}  console.log(sum(1, 2, 3, 4, 5)); // 输出: 15

从数组中提取数据:

可以使用Rest参数将数组中的元素作为参数传递给函数。

const arr = [1, 2, 3, 4];  
function printNumbers(...numbers) {  numbers.forEach(num => console.log(num));  
}  printNumbers(...arr); // 输出: 1 2 3 4

结合其他参数使用:

Rest参数可以与其他参数一起使用,但必须放在参数列表的最后。

function processValues(operation, ...values) {  if (operation === 'sum') {  return values.reduce((acc, val) => acc + val, 0);  } else if (operation === 'average') {  const sum = values.reduce((acc, val) => acc + val, 0);  return sum / values.length;  }  return null;  
}  console.log(processValues('sum', 1, 2, 3, 4)); // 输出: 10  
console.log(processValues('average', 1, 2, 3, 4, 5)); // 输出: 3

三、注意事项

位置要求:
Rest参数必须放在参数列表的最后,且一个函数中只能有一个Rest参数。

参数解构:
Rest参数可以被解构,但需要注意解构后的变量名与数组元素的对应关系。

function f(...[a, b, c]) {  return a + b + c;  
}  console.log(f(1, 2, 3)); // 输出: 6  
console.log(f(1, 2, 3, 4)); // 输出: 6(第四值没有与之对应的变量名)

函数length属性:

函数的length属性返回的是没有Rest参数时的参数个数。

function example(a, b, ...c) {}  
console.log(example.length); // 输出: 2

四、与扩展运算符的区别

虽然Rest参数和扩展运算符(Spread operator)都用到了三个点(...),但它们的作用和用途是不同的。Rest参数用于函数定义中,用于收集剩余的参数;而扩展运算符用于数组、对象等可迭代对象的展开。

// 扩展运算符示例  
const arr1 = [1, 2, 3];  
const arr2 = [...arr1, 4, 5]; // 将arr1的元素展开到arr2中  console.log(arr2); // 输出: [1, 2, 3, 4, 5]

数组中的扩展运算符

扩展运算符用三个点号(...)表示,用于将数组元素展开到不同的地方。

示例1:合并数组
const arr1 = [1, 2, 3]; 
const arr2 = [4, 5, 6]; 
const mergedArray = [...arr1, ...arr2]; 
console.log(mergedArray); // 输出: [1, 2, 3, 4, 5, 6]
示例2:在数组字面量中使用
const elements = ['fire', 'air']; 
const nature = ['earth', ...elements, 'water']; 
console.log(nature); // 输出: ['earth', 'fire', 'air', 'water']
示例3:将类数组对象转换为数组
const arrayLike = {0: 'a', 1: 'b', length: 2}; 
const arr = [...arrayLike]; 
console.log(arr); // 输出: ['a', 'b']
示例4:复制数组
const originalArray = [1, 2, 3]; 
const copiedArray = [...originalArray]; 
console.log(copiedArray); // 输出: [1, 2, 3]

函数中的剩余参数

剩余参数用三个点号(...)表示,用于将函数接收到的所有剩余参数收集到一个数组中。

示例1:基本用法
function sum(...numbers) { return numbers.reduce((total, num) => total + num, 0); } console.log(sum(1, 2, 3, 4)); // 输出: 10
示例2:结合普通参数使用
function multiply(factor, ...numbers) { 
return numbers.map(num => num * factor); 
} 
console.log(multiply(2, 1, 2, 3, 4)); // 输出: [2, 4, 6, 8]

对象中的扩展运算符

在 ES2018 中,扩展运算符也被引入到了对象中,用于合并和克隆对象。

示例1:合并对象
const obj1 = {a: 1, b: 2}; 
const obj2 = {b: 3, c: 4}; 
const mergedObj = {...obj1, ...obj2}; 
console.log(mergedObj); // 输出: {a: 1, b: 3, c: 4}
示例2:克隆对象
const originalObj = {a: 1, b: 2}; 
const clonedObj = {...originalObj}; 
console.log(clonedObj); // 输出: {a: 1, b: 2}
示例3:结合数组和对象使用
const people = [ 
{name: 'Alice', age: 25}, 
{name: 'Bob', age: 30} 
]; 
const peopleWithCities = people.map(person => ({...person, city: 'New York'})); 
console.log(peopleWithCities); 
// 输出: [{name: 'Alice', age: 25, city: 'New York'}, {name: 'Bob', age: 30, city: 'New York'}]
注意事项
  1. 数组和对象的浅拷贝:扩展运算符执行的是浅拷贝,即只复制了对象的第一层属性。对于嵌套的对象或数组,深层次的引用仍会保留。
  2. 函数参数中的默认值:剩余参数不能用于设置默认参数值。

7.Symbol()类型运用

Symbol 是 ES6(ECMAScript 2015)中引入的一种新的原始数据类型,表示独一无二的值。与字符串和数字不同,每次创建一个新的 Symbol 时,即使它的描述相同,它们也是不同的值。这使得 Symbol 类型非常适合用作对象的唯一属性键,以避免属性名冲突。

创建 Symbol

要创建一个新的 Symbol,你可以使用 Symbol() 函数,并传递一个可选的描述字符串(该描述仅用于调试目的,不会影响 Symbol 的唯一性):

const sym1 = Symbol('description');  
const sym2 = Symbol('description');  
console.log(sym1 === sym2); // false  
console.log(sym1.toString()); // "Symbol(description)"  
console.log(sym2.toString()); // "Symbol(description)"
使用 Symbol 作为对象属性键

Symbol 可以用作对象的属性键,这样可以确保属性键的唯一性:

const sym = Symbol('uniqueKey');  
const obj = {  [sym]: 'This is a unique property'  
};  console.log(obj[sym]); // "This is a unique property"  // 使用 for...in 循环无法遍历 Symbol 类型的属性  
for (let key in obj) {  console.log(key); // 不会输出任何内容  
}  // 使用 Object.keys() 也不会列出 Symbol 类型的属性  
console.log(Object.keys(obj)); // []  // 使用 Object.getOwnPropertySymbols() 可以获取 Symbol 类型的属性  
console.log(Object.getOwnPropertySymbols(obj)); // [Symbol(uniqueKey)]  // 使用 Object.getOwnPropertyNames() 也不会列出 Symbol 类型的属性  
console.log(Object.getOwnPropertyNames(obj)); // []
全局 Symbol 注册表

Symbol 还提供了一个全局注册表,使用 Symbol.for() 方法。此方法会检查传入的字符串是否已经存在于全局 Symbol 注册表中,如果存在则返回该 Symbol,否则创建一个新的 Symbol 并注册到表中:

const symGlobal1 = Symbol.for('globalKey');  
const symGlobal2 = Symbol.for('globalKey');  console.log(symGlobal1 === symGlobal2); // true

与直接调用 Symbol() 创建的 Symbol 不同,通过 Symbol.for() 创建的 Symbol 是全局唯一的,即使它们在不同的代码块或文件中创建。

内置 Symbol 属性

JavaScript 还定义了一些内置的 Symbol 属性,这些属性通常用于对象方法的钩子(traps),如:

  • Symbol.iterator:定义对象的默认迭代行为。
  • Symbol.toPrimitive:定义对象在转换为原始值时的行为。
  • Symbol.toStringTag:定义对象在 Object.prototype.toString.call() 时的返回值。

例如,定义一个可迭代对象:

const iterable = {  [Symbol.iterator]() {  let i = 0;  const data = [1, 2, 3];  return {  next() {  if (i < data.length) {  return { value: data[i++], done: false };  } else {  return { done: true };  }  }  };  }  
};  for (let value of iterable) {  console.log(value); // 1, 2, 3  
}

8.ES6-迭代器

ES6 引入了迭代器(Iterator)的概念,它是一种统一遍历不同数据结构(如数组、对象、Map、Set 等)的方式。迭代器对象实现了迭代协议,该协议规定了 next() 方法,该方法会返回迭代结果的对象,该对象包含两个属性:value 和 done。value 表示当前遍历到的值,done 是一个布尔值,表示遍历是否结束。

以下是关于 ES6 迭代器的一些关键点和用法示例:

可迭代对象(Iterable)

首先,要明白什么是可迭代对象。一个对象如果实现了 @@iterator 方法(在对象上或通过其原型链),那么它就是可迭代的。@@iterator 方法应该返回一个迭代器对象。

默认迭代器

对于内置的可迭代对象(如数组、字符串、Map 和 Set),JavaScript 提供了默认的迭代器。

const arr = [1, 2, 3];  
const iter = arr[Symbol.iterator]();  console.log(iter.next()); // { value: 1, done: false }  
console.log(iter.next()); // { value: 2, done: false }  
console.log(iter.next()); // { value: 3, done: false }  
console.log(iter.next()); // { value: undefined, done: true }
自定义迭代器

你也可以为自定义对象实现迭代器。为此,你需要在对象上定义 @@iterator 方法,或者在其原型链上定义。

const myIterable = {  data: [1, 2, 3],  [Symbol.iterator]() {  let index = 0;  const data = this.data;  return {  next() {  if (index < data.length) {  return { value: data[index++], done: false };  } else {  return { value: undefined, done: true };  }  }  };  }  
};  for (const value of myIterable) {  console.log(value); // 1, 2, 3  
}
使用 for...of 循环

for...of 循环是遍历可迭代对象的一种简洁方式。

const str = 'hello';  
for (const char of str) {  console.log(char); // h, e, l, l, o  
}

迭代器的高阶应用

迭代器可以用于创建更高级的数据处理功能,如生成器(Generator)、解构赋值(destructuring assignment with rest)、扩展运算符(spread operator)等。

生成器函数(Generator Function)

生成器函数是 JavaScript ES6 引入的一种特殊类型的函数,它允许你暂停和恢复函数的执行。生成器函数使用 function* 语法来定义,并且可以在函数体内使用 yield 关键字来暂停函数的执行并返回一个值。每次调用生成器函数的 .next() 方法时,函数会从上次暂停的地方继续执行,直到遇到下一个 yield 或函数结束。

function* numberGenerator() {  yield 1;  yield 2;  yield 3;  
}  const gen = numberGenerator();  console.log(gen.next()); // { value: 1, done: false }  
console.log(gen.next()); // { value: 2, done: false }  
console.log(gen.next()); // { value: 3, done: false }  
console.log(gen.next()); // { value: undefined, done: true }

生成器函数传参情况

//生成器函数
function* myGenerator(a,b,c) {  yield a;  yield b;  yield c;yield a+b+c;  
}  const gen=myGenerator(4,5,6); 
console.log(gen.next().value); // 4
console.log(gen.next().value); // 5
console.log(gen.next().value); // 6
console.log(gen.next().value); // 15
console.log(gen.next().done); // true
console.log(gen.next().value); // undefined
for (const value of myGenerator(1,2,3)) {  console.log(value); 
}
解构赋值与扩展运算符

解构赋值和扩展运算符都可以与迭代器一起使用,以简洁的方式处理可迭代对象。

const [first, ...rest] = [1, 2, 3, 4];  
console.log(first); // 1  
console.log(rest);  // [2, 3, 4]  const arrCopy = [...arr]; // 使用扩展运算符复制数组

9.ES6-class关键字

ES6引入了类(class)的概念,使面向对象编程在JavaScript中变得更加直观和易于管理。以下是关于ES6类属性以及继承的一些基本介绍和示例。

类属性

在ES6中,你可以在类中定义属性(包括静态属性和实例属性)。虽然ES6本身并没有直接提供类的实例属性的简洁语法,但可以通过在构造函数中定义或者在类字段语法(从ES2022/ES13开始引入)中定义属性。

在构造函数中定义属性
class Person { 
constructor(name, age) { 
this.name = name; 
this.age = age; 
} greet() { 
console.log(`Hello, my name is ${this.name} and I am ${this.age} years old.`); 
} 
} const person = new Person('Alice', 30); 
person.greet(); // Hello, my name is Alice and I am 30 years old.
使用类字段语法定义属性(ES2022/ES13+)
class Person { 
name; 
age; constructor(name, age) { 
this.name = name; 
this.age = age; 
} greet() { 
console.log(`Hello, my name is ${this.name} and I am ${this.age} years old.`); 
} 
} const person = new Person('Alice', 30); 
person.greet(); // Hello, my name is Alice and I am 30 years old.

类字段语法还支持在声明时直接初始化属性:

class Person { 
name = 'Unknown'; 
age = 0; greet() { 
console.log(`Hello, my name is ${this.name} and I am ${this.age} years old.`); 
} 
} const person = new Person(); 
person.greet(); // Hello, my name is Unknown and I am 0 years old.

静态属性(Static Properties)

静态属性属于类本身,而不是类的实例。它们使用 static 关键字定义。

class MathUtils { 
static PI = 3.14159; static circleArea(radius) { 
return MathUtils.PI * radius * radius; 
} 
} console.log(MathUtils.PI); // 3.14159 
console.log(MathUtils.circleArea(5)); // 78.53975

继承

在ES6中,你可以使用 extends 关键字实现类的继承。子类可以使用 super 关键字调用父类的构造函数和方法。

class Animal { 
constructor(name) { 
this.name = name; 
} speak() { 
console.log(`${this.name} makes a sound.`); 
} 
} class Dog extends Animal { 
constructor(name, breed) { 
super(name); // 调用父类的构造函数 
this.breed = breed; 
} speak() { 
super.speak(); // 调用父类的方法 
console.log(`${this.name} barks.`); 
} 
} const dog = new Dog('Buddy', 'Golden Retriever'); 
dog.speak(); 
// Buddy makes a sound. 
// Buddy barks.

静态方法的继承

静态方法不能被实例调用,也不能被子类的实例重写(尽管它们可以在子类中重新定义)。

class Parent { 
static greet() { 
console.log('Hello from Parent'); 
} 
} class Child extends Parent { 
static greet() { 
console.log('Hello from Child'); 
} 
} Parent.greet(); // Hello from Parent 
Child.greet(); // Hello from Child

在这个例子中,Child 类有自己的 greet 静态方法,调用 Child.greet() 会输出 "Hello from Child",而不是从 Parent 类继承的方法。

总结

  • 类属性:可以在构造函数中定义,或者在类字段语法中直接声明和初始化。
  • 静态属性:使用 static 关键字定义,属于类本身而不是实例。
  • 继承:使用 extends 关键字实现,super 关键字用于调用父类的构造函数和方法。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/55914.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

CSS元素显示类型

display 属性是 CSS 中最重要的属性之一&#xff0c;主要用来控制元素的布局&#xff0c;通过 display 属性您可以设置元素是否显示以及如何显示。 根据元素类型的不同&#xff0c;每个元素都有一个默认的 display 属性值&#xff0c;例如<div>默认的 display 属性值为 …

电脑端视频通过PCIE到FPGA端转UDP网络视频输出,基于XDMA+PHY芯片架构,提供3套工程源码和技术支持

目录 1、前言工程概述免责声明 2、相关方案推荐我已有的PCIE方案我这里已有的以太网方案 3、PCIE基础知识扫描4、工程详细设计方案工程设计原理框图电脑端视频PCIE视频采集QT上位机XDMA配置及使用XDMA中断模块FDMA图像缓存UDP视频组包发送UDP协议栈MAC数据缓冲FIFO组Tri Mode E…

STM32编码器接口

一、概述 1、Encoder Interface 编码器接口概念 编码器接口可接收增量&#xff08;正交&#xff09;编码器的信号&#xff0c;根据编码器旋转产生的正交信号脉冲&#xff0c;自动控制CNT自增或自减&#xff0c;从而指示编码器的位置、旋转方向和旋转速度每个高级定时器和通用…

CSS 3D转换

在 CSS 中&#xff0c;除了可以对页面中的元素进行 2D 转换外&#xff0c;您也可以对象元素进行 3D转换&#xff08;将页面看作是一个三维空间来对页面中的元素进行移动、旋转、缩放和倾斜等操作&#xff09;。与 2D 转换相同&#xff0c;3D 转换同样不会影响周围的元素&#x…

CVE-2024-36971漏洞修复----Debian 10.13 内核升级

CVE-2024-36971漏洞修复---Debian 10.13 内核升级 1. 下载内核2. 安装依赖包3. 二进制安装3.1 上传3.2 解压3.3 修改配置文件3.4 编译3.5 安装内核及模块 4. 重启服务器并确认升级成功 1. 下载内核 到kernel.org下载新版的Kernel 由于开发那边不想让Kernel跨大版本,所以就升级…

OpenCV高级图形用户界面(1)创建滑动条函数createTrackbar()的使用

操作系统&#xff1a;ubuntu22.04 OpenCV版本&#xff1a;OpenCV4.9 IDE:Visual Studio Code 编程语言&#xff1a;C11 算法描述 创建一个滑动条并将其附加到指定的窗口。 该函数 createTrackbar 创建一个具有指定名称和范围的滑动条&#xff08;滑块或范围控制&#xff09;…

机器学习笔记-1

文章目录 前言一、How to find a function二、Define Loss from Training Data三、Optimization总结 前言 机器学习&#xff08;Machine Learning, ML&#xff09;是一门让计算机通过数据来自动学习和改进的技术。它的核心理念是通过分析大量的历史数据来找到其中的规律&#…

Qt-链接数据库可视化操作

1. 概述 Qt 能够支持对常见数据库的操作&#xff0c;例如&#xff1a; MySQL、Oracle、SqlServer 等等。 Qt SQL模块中的API分为三层&#xff1a;驱动层、SQL接口层、用户接口层。 驱动层为数据库和SQL接口层之间提供了底层的桥梁。 SQL接口层提供了对数据库的访问&#xff0…

蓝桥杯【物联网】零基础到国奖之路:十六. 扩展模块之矩阵按键

蓝桥杯【物联网】零基础到国奖之路:十六. 扩展模块之矩阵按键 第一节 硬件解读第二节 CubeMX配置第三节 MDK代码 第一节 硬件解读 扩展模块和ADC模块是一摸一样的&#xff0c;插在主板上。 引脚对应关系&#xff1a; PB6-ROW1 PB7-ROW2 PB1-COLUMN1 PB0-COLUMN2 PA8-COLUMN3 …

adb安装教程(Windows10)

本章教程&#xff0c;主要介绍如何在Windows10操作系统上安装adb。 一、adb简介 ADB&#xff0c;全称为Android Debug Bridge&#xff0c;是Android开发中一个重要的命令行工具。它用于与Android设备进行通信&#xff0c;提供了多种功能来帮助开发者进行调试和应用管理。 二、下…

Qt第三课 ----------显示类的控件属性

作者前言 &#x1f382; ✨✨✨✨✨✨&#x1f367;&#x1f367;&#x1f367;&#x1f367;&#x1f367;&#x1f367;&#x1f367;&#x1f382; ​&#x1f382; 作者介绍&#xff1a; &#x1f382;&#x1f382; &#x1f382; &#x1f389;&#x1f389;&#x1f389…

美团Java一面

美团Java一面 9.24一面&#xff0c;已经寄了 收到的第一个面试&#xff0c;表现很不好 spring bean生命周期 作用域&#xff08;忘完了&#xff09; 为什么用redis缓存 redis和数据库的缓存一致性问题 redis集群下缓存更新不一致问题 aop说一下 arraylist和linkedlist 数据库的…

kali(专业的渗透测试虚拟机)|kali下载链接地址 |kali安装 |kali部署指南

介绍 kali 是Debian开源linux系统体系下的子分支之一 Debian-kali 扩展&#xff1a;Ubuntu也是Debian开源linux系统体系下的子分支之一 Debian-ubuntu 安装kali 2023.03 稳定版 Index of /kali-images/kali-2023.1/ 安装可以参考他的教程&#xff0c; 写的很详细了…

C语言-数据结构 折半查找

在折半查找中&#xff0c;刚开始学可能会在下标处产生困惑&#xff0c;例如奇数个长度的数组怎么处理&#xff0c;偶数个长度的数组怎么处理&#xff0c;不需要修改代码吗&#xff1f;并且下标我从1开始算和0开始算影响代码吗&#xff1f;其实都可以用一样的代码&#xff0c;产…

nginx 资料整理(三)- web

nginx 资料整理&#xff08;三&#xff09; 1. web服务器1. 日志功能1. 访问日志2. 错误日志3. 实例演示 2. 网站功能列表1. autoindex2. autoindex_localtime 3. 认证功能1. auth_basic2. 实例演示 4. 访问控制功能1. allow & deny2. 局限性3. 实例演示 5. 状态模块1. stu…

论文阅读:Split-Aperture 2-in-1 Computational Cameras (二)

Split-Aperture 2-in-1 Computational Cameras (一) Coded Optics for High Dynamic Range Imaging 接下来&#xff0c;文章介绍了二合一相机在几种场景下的应用&#xff0c;首先是高动态范围成像&#xff0c;现有的快照高动态范围&#xff08;HDR&#xff09;成像工作已经证…

多种方式确定Linux是CentOS还是Ubuntu

目录 前言正文 前言 对应的基本知识比较少&#xff0c;以下只是记录总结 由于目前使用的是centos&#xff0c;后续找到linux会对应补充 正文 要确定Linux系统是CentOS还是Ubuntu&#xff0c;可以通过以下几种方式进行分析 一、查看发行版信息文件&#xff1a; CentOS&…

校园系统校园小程序 论坛校园圈系统失物招领、闲置二手、跑腿外卖等校园圈子系统应该具备有哪些功能

针对校园系统、校园小程序、论坛校园圈系统以及失物招领、闲置二手、跑腿外卖等具体功能&#xff0c;一个综合性的校园圈子系统应该具备以下主要功能&#xff1a; 前后端源码查看 一、基础功能 用户注册与登录 提供用户注册和登录功能&#xff0c;支持学生身份验证、手机号验…

WireShark过滤器

文章目录 1. **捕获过滤器&#xff08;Capture Filter&#xff09;**语法格式&#xff1a;常见捕获过滤器示例&#xff1a; 2. **显示过滤器&#xff08;Display Filter&#xff09;**语法格式&#xff1a;常见比较运算符&#xff1a;常见显示过滤器示例&#xff1a;逻辑操作符…

Linux系统:apt-get update 和apt update区别

apt-get update 和apt update区别 ‌apt-get update和apt update的主要区别在于它们所属的命令集以及在现代Ubuntu系统中的使用推荐。‌ ‌所属命令集‌&#xff1a;apt-get update是apt-get命令的一部分&#xff0c;而apt update是apt命令的一部分。apt是apt-get的替代工具&am…