本文深入解析JavaScript中Class类的静态属性与方法。通过static关键字定义静态成员,它们归属于类本身而非实例,无法被实例直接访问或继承。文章对比了静态与非静态成员在内存存储、生命周期及访问方式上的区别,并列举了静态方法的使用限制,如不能访问this及非静态成员。
一、类的两个概念
1、类自身;
2、类的实例对象;
总体而言,静态成员指向的是类本身,而非类的实例对象。这种归属关系的差异是理解静态属性和静态方法核心逻辑的关键。
二、对象的两个部分
1、属性
属性可分为:实例属性、静态属性(也称类属性)以及只读属性。
2、方法
方法可分为:实例方法和静态方法(也称类方法)。
class Person {
//1、定义方法
/* 1.1、实例属性,直接定义的属性,要new实例后,实例去访问的*/
name= "tom";
age = 10;
/* 1.2、静态属性(类属性),通过static开头的属性,Person类可以访问,
不需要创建实例,实例访问不到 */
static height = 180;
/* 1.3、只读属性,readonly开头的属性,只可读,不可改*/
readonly money= 1000;
//2、定义方法
say(){
console.log('hello world');
}
static work(){
console.log('我能挣钱');
}
}
const per = new Person();
//per.money=2000 报错,不可修改
console.log(per, Person.height);
per.say() //调用实例方法
Person.work() //调用类方法三、静态方法使用:在方法前加上static关键字
1、为什么使用静态方法
使用static关键字的主要目的是阻止该方法被实例继承。在类的内部,直接定义的方法相当于定义在原型上,会被类的实例所继承;而使用static定义的静态方法则不会被实例继承。
class User{
static call(){
console.log('你好呀');
}
}
User.call()//你好呀
let ff = new User()
ff.call()//报错,实例不能访问类的静态方法例如,类User可以直接调用call方法,但其实例ff却无法直接访问该方法。
不过,我们可以通过继承机制,让另一个类来继承User中的方法。
class User{
static call(){
console.log('你好呀');
}
}
class foo extends User{}
foo.call()//'你好呀' 如上所示,foo类通过继承User类,从而可以使用User中的静态方法。
我们知道class类是ES6之后引入的新特性,如果使用早期的ES5语法来实现,代码如下:
class User{
static call(){
console.log('静态方法的你好呀');
}
call(){
console.log('构造函数方法的你好呀');
}
}
//等同于
function User(){}
User.call=function(){
console.log('静态方法的你好呀');
}
User.prototype.call=function(){
console.log('构造函数方法的你好呀');
}但在User类中,构造函数方法是可以被实例调用的,具体表现如图:
function User(){}
User.prototype.call=function(){
console.log('你好呀');
}
let h1 =new User()
h1.call()//你好呀完整的ES5实现代码如下:
class User {
call() {
// 这里面的this指向构造函数的对象
console.log(this === hh); // true
console.log("构造函数方法的你好呀");
}
static call() {
// 这里面的this指向类本身
console.log(this === User); // true
console.log("静态方法的你好呀");
}
}
// 静态方法
User.call(); //静态方法的你好呀
// 构造函数方法
let hh = new User();
hh.call(); //构造函数方法的你好呀三、总结
1、静态属性和非静态属性的区别
- 内存存放位置不同:所有由static修饰的属性和方法都存放在内存的方法区中,而非静态成员则存储在堆内存中。
- 出现时机不同:静态属性和方法在对象创建之前就已经存在,而非静态成员只有在创建对象后才存在。
- 静态属性是整个类共用的。
- 生命周期不同:静态成员在类消失后被销毁,而非静态成员在对象销毁后随之销毁。
- 访问方式不同:静态成员可以直接通过类名访问,而非静态成员只能通过对象实例进行访问。
2.使用static的注意事项
- 带有静态修饰符的方法只能访问静态属性。
- 非静态方法既能访问静态属性,也能访问非静态属性。
- 非静态方法中不能定义静态变量。
- 静态方法中不能使用this关键字。
- 静态方法不能调用非静态方法,但非静态方法可以调用静态方法。
以上为个人经验,希望能给大家一个参考,也希望大家多多支持本站。