Vue基础知识-重要的内置关系:vc实例.__proto__.__proto__ === Vue.prototype

前言

在 JavaScript 中,原型链 是实现继承的核心机制,也是理解框架设计(如 Vue)的重要基础。而 Vue 组件(VueComponent)的原型设计,更是直接依赖于 JS 原型链的特性 ------ 通过原型链关联,让组件实例(vc)能访问 Vue 原型上的属性和方法。

一、完整源码

html 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script src="../js/vue.js"></script>
</head>
<body>
    <div id="root">
        <student></student>
    </div>
</body>
    <script>
        
       
/*        
        function Person(){
            this.name = "张三"
        }
        此时Person有自己的原型,其原型的原型(Person.prototype.prototype)是Object的原型(Object.prototype)
        访问原型方式(两者等价):
            1 Person实例.__proto__
            2 Person.prototype

        Person.prototype.age = 18 //通过类给原型添加属性
        let person = new Person()  
        person.__proto__.sex = '男'//通过对象给原型添加属性
        console.log(new Person())  //Person对象有自己的属性name和原型属性age、sex

        对象访问属性时:
            1 找自身实例是否有该属性;
            2 找实例的原型是否有该属性(如Person实例.__proto__);
            3 就继续顺着原型链往上找(如Person实例.__proto__.__proto__,此时为Object的原型)
            4 Object的原型的原型为null(返回 undefined)。
*/
        
        const student = Vue.extend({
            template:`
                <div>
                    <h1>学生名称:{{name}}</h1>
                    <h1>学生年龄:{{age}}</h1>
                </div>
            `,
            data() {
                return {
                    name:'张三',
                    age:'18'
                }
            }
        })
        const vm = new Vue({
            el:'#root',
            data() {
                return {
                    n:1
                }
            },
            components:{ 
                student
           
            }
        })
       /* 
            重要的内置关系:new student().__proto__.__proto__ === Vue.prototype。即VueComponent原型的原型===Vue的原型
            因此,vc可以访问Vue原型上的属性、方法 
        */
        console.log(new student().__proto__.__proto__ === Vue.prototype) // true
    </script>
</html>

二、核心知识点解析

1. JavaScript 原型链:从 Person 构造函数说起

原型链的核心逻辑是:每个实例对象都有一个__proto__(原型),其__proto__又指向更高层的原型,直到指向Object原型对象.__proto__ = null(原型链终点)

1.1 代码中原型链的关键操作
  • 构造函数与实例的关系new Person()创建的实例,其__proto__ === Person.prototype(这是原型链的起点)。

    javascript 复制代码
    let p = new Person();
    console.log(p.__proto__ === Person.prototype); // true
  • 两种操作原型的方式

    1. 通过构造函数操作:Person.prototype.age = 18(直接给Person的原型添加age属性);
    2. 通过实例操作:person.__proto__.sex = '男'(实例的__proto__就是Person.prototype,本质和第一种方式一致)。
  • 原型链查找规则 :当访问实例的属性时,会优先查找自身属性 → 若没有则找__proto__(构造函数原型)→ 再找__proto__.__proto__(更高层原型)→ 直到null(找不到返回undefined)。
    例如访问new Person().age:实例自身没有age → 找Person.prototype.age(存在,返回 18)。

2. Vue 组件原型关系:为什么 VC 能访问 Vue 原型的方法?

Vue 中的组件(VueComponent,简称VC)是通过Vue.extend创建的构造函数,其原型设计直接依赖 JS 原型链,核心结论是:VC实例.__proto__.__proto__ === Vue.prototype

2.1 代码中验证
javascript 复制代码
console.log(new student().__proto__.__proto__ === Vue.prototype); // true
2.2 这个设计的意义是什么?

Vue 的原型(Vue.prototype)上挂载了很多全局方法(如$emit$on$nextTick等)。通过将VC的原型链指向Vue.prototypeVC实例就能直接访问这些方法,无需重复定义,实现了方法复用。

例如,我们可以在Vue.prototype上添加一个全局方法,然后在组件中直接调用:

javascript 复制代码
// 给Vue原型添加全局方法
Vue.prototype.sayHi = function() {
    alert('Hi,我是Vue原型上的方法!');
};

// 在student组件中调用
const student = Vue.extend({
    template: `
        <div>
            <!-- 其他内容 -->
            <button @click="sayHi">调用全局方法</button>
        </div>
    `,
    // ...其他配置
});

点击按钮时,VC实例会通过原型链找到Vue.prototype.sayHi,成功执行方法。

相关推荐
玖釉-几秒前
解决PowerShell执行策略导致的npm脚本无法运行问题
前端·npm·node.js
Larcher34 分钟前
新手也能学会,100行代码玩AI LOGO
前端·llm·html
徐子颐1 小时前
从 Vibe Coding 到 Agent Coding:Cursor 2.0 开启下一代 AI 开发范式
前端
小月鸭1 小时前
如何理解HTML语义化
前端·html
jump6801 小时前
url输入到网页展示会发生什么?
前端
诸葛韩信1 小时前
我们需要了解的Web Workers
前端
brzhang2 小时前
我觉得可以试试 TOON —— 一个为 LLM 而生的极致压缩数据格式
前端·后端·架构
yivifu2 小时前
JavaScript Selection API详解
java·前端·javascript
这儿有一堆花2 小时前
告别 Class 组件:拥抱 React Hooks 带来的函数式新范式
前端·javascript·react.js
十二春秋2 小时前
场景模拟:基础路由配置
前端