Vue2从源码角度来回答一些常见的问题

1.请说一下Vue2响应式数据的理解(先知道基本的问题在哪里,源码的角度来回答,用的时候会有哪些问题)

可以监控一个数据的修改和获取操作。针对对象格式会给每个对象的属性进行劫持 Object.defineProperty

源码层面 initData -> observe -> defineReactive方法(内部对所有属性进行了重写 性能问题) 递归增加对象中的对象增加getter和setter

我们在使用Vue的时候,如果层级过深(考虑优化) 如果数据不是响应式的就不要放在data中了。我们属性取值的时候尽量避免多次取值。
如果有些对象是放到data中的但是不是响应式的可以考虑采用Object.freeze()来冻结对象

let total 
for(let i = 0; i < 100; i++) {
    // this.timer += i
    total += i
}
this.timer = total;

2.Vue中如何检测数组变化?

vue2中检测数组的变化并没有采用defineProperty 因为修改索引的情况不多(如果直接使用defineProperty会浪费大量性能) 采用重写数组的变异方法来实现(函数劫持)

initData -> observe -> 对我们传入的数组进行原型链修改,后续调用的方法都是重写后的方法 ->对数组中每个对象也再次进行代理

修改数组索引,修改长度是无法进行监控的 arr[1] = 100; arr.length = 300; 不会触发视图更新

arr[0].xxx = 100; 因为数组中的对象会被observe

3.Vue中如何进行依赖收集?

  • 所谓的依赖收集(观察者模式) 被观察者指代的是数据(dep),观察者(watcher 3种watcher,渲染watcher,计算属性,用户watcher)
  • 一个watcher中可能对应着多个数据,watcher中还需要保存dep(重新渲染的时候,可以让属性重新记录watcher),计算属性也会用到

多对多的关系 一个dep对应多个watcher,一个watcher有多个dep。默认渲染的时候会进行依赖收集(会触发get方法),数据更新了就找到属性对应的watcher去触发更新

取值的时候收集依赖,设值的时候更新试图

4.如何理解Vue中模板编译原理

我们用户传递的是template属性,我们需要将这个template编译成render函数

  • template -> ast语法树
  • 对语法树进行标记(标记的是静态节点)
  • 对语法树生成render函数

最终每次渲染可以调用render函数返回对应的虚拟节点(递归是先子后父) I

5.Vue生命周期钩子是如何实现的

就是内部利用了一个发布订阅模式,将用户写的钩子维护成了一个数组,后续一次调用 callHook

内部就是一个发布订阅模式

为什么有些钩子的执行是先子后父亲,有些是先父后子,组件渲染是如何渲染的

// 遇到父组件就先渲染父组件
<div id='app'>
    // 遇到子组件就渲染子组件
    <my-button >
    // 先渲染子组件后,完成才能渲染完毕父组件
</div>

6.Vue的生命周期方法有哪些?一般在哪一步发送请求及原因

beforeCreate 这里没有实现响应式数据 vue3中不需要了 没用
created √ 拿到的是响应式数据(不涉及到dom渲染),这个api可以在服务端渲染中使用
beforeMount
mounted √ 可以获取$el
beforeUpdate
updated
actived
deactivated
beforeDestroy √ 手动调用移除会触发
destroyed √ 销毁后触发
errorCaptured 捕获错误

-> 一般最多是在mounted(created不是比mounted早嘛?代码是同步进行的,请求是异步的)

7.Vue.mixin的使用场景和原理

我们可以通过Vue.mixin来实现逻辑的复用,问题在于数据来源不明确。声明的时候可能会导致命名冲突。高阶组件,vue3采用的就是compositionAPI解决了复用问题

Vue.mixin({
    data() {
        return {xxx:11}
    },
    beforeCreate() {
        this.$store = new Store()
    },
    beforeDestory() {

    }
})
Vue.component('my', {
    data() {
        return { xxx: 222 }
    },
    template: '{{xxx}}'
})

8.Vue组件data为什么必须是个函数?

原因就在于针对根实例而言,new Vue, 组件时通过同一个构造函数多次创建实例,如果同一个对象的话,那么数据会被相互影响;每个组件的数据源
都是独立的,那就每次都调用data返回一个新对象。

const Vue = {}
function Sub() {}
Vue.extend = function(options) {
    function Sub() {
        this.data = this.constructor.options.data()
    }
    Sub.options = options;
    return Sub;
}
let Child = Vue.extend({
    data() {
        return { a: 1}
    }
})
let c1 = new Child()
c1.data.a = 100;
let c2 = new Child()
console.log(c2.data.a);

9.nextTick在哪里使用?原理是?

nextTick内部采用了异步任务进行了包装(多个nextTick调用会被合并成一次 内部会合并回调) 最后在异步任务中批处理
主要应用场景就是异步更新(默认调度的时候 就会添加一个nextTick任务) 用户为了获取最终的渲染结果需要在内部任务执行之后再执行用户逻辑
这时候用户需要将对应的逻辑放到nextTick中

  • nextTick 只是将异步任务维护到队列中,并不是会开一个定时器,不是创建了一个异步任务,而是将这个任务维护到了队列中,
  • nextTick将任务放到队列中是同步任务,刷新的方法是异步执行的

10.computedwatch区别

computed 和 watch的相同点:底层都会创建一个watcher(用法区别:computed定义的属性可以在模板中使用,watch不能在试图中使用)

  • computed 默认不会立即执行,只有取值的时候才会去执行 内部会有唯一一个dirty属性,来控制依赖的值是否发生变化。默认计算属性需要同步返回结果
  • watch 默认用户会提供一个回调函数,数据变化了就调用这个回调。我们可以监控某个数据的变化,数据变化了执行某个操作。

11.vue.set方法是如何实现的

Vue.set 方法时vue中的补丁方法。(正常添加的属性时不会触发更新的,我们数组无法监控索引和长度)

如何实现的 我们给每一个对象都增添了一个dep属性

vue3中也不需要此方法了(当属性添加或删除时 手动触发对象本身dep来进行更新)

12.Vue为什么需要虚拟DOM

  • 主要这个虚拟dom的好处是什么? 我们写的代码可能会针对不同的平台来使用(weex, web, 小程序) 可以跨平台,不需要考虑平台问题
  • 不用关心兼容性问题,可以在上层将对应的渲染方法传递给我,我来通过虚拟dom渲染即可

diff算法:针对更新的时候,有了虚拟dom之后我们可以通过diff算法来找到最后的差异进行修改真实dom(类似于在真实dom之间做了一层缓存)

跨平台、diff算法

13.Vuediff算法原理

diff算法的特点就是平级比较,内部采用了双指针方式进行了优化 优化了常见的操作。采用了递归比较的方式。

针对一个节点的diff算法

  • 先拿出根节点来进行比较如果是同一个节点则比较属性,如果不是同一个节点则直接换成最新的即可
  • 同一个节点比较属性后,复用老节点

比较儿子

  • 一方有儿子 一方没儿子(删除、添加)
  • 两方都有儿子
    • 优化比较 头头 尾尾 交叉比对
    • 就做一个映射表,用新的去映射表中查找此元素是否存在,存在则移动不存在则插入,最后删除多余的。
    • 这里会有多移动的情况

O(n)复杂度的递归比较

14.既然Vue通过数据劫持可以精准探测数据变化,为什么还需要虚拟DOM进行diff检测差异

  • 如果给每个属性都去增加watcher,而且粒度太小也是不好控制,降低watcher的数量(每一个组件都有一个watcher) 可以通过diff算法来优化渲染过程。
    通过diff算法和响应式原理折中处理一下

15.请说明Vue中key的作用和原理,谈谈你对它的理解

isSameVnode中会根据key来判断两个元素是否是同一个元素,key不相同说明不是同一个元素(key在动态列表中不要使用索引 -> bug)
我们使用key尽量保证key的唯一性(这样可以优化diff算法)

16. 谈一谈对Vue组件化的理解

组件的优点: 组件的复用可以根据数据渲染对应的组件,把组件相关的内容放在一起(方便复用)合理规划组件,可以做到更新的时候是组件级更新
(组件化中的特性:属性,事件,插槽)

Vue中怎样处理组件
1. Vue.extend 根据用户的传入的对象生成一个组件的构造函数
2. 根据组件产生对应的虚拟节点 data:{hook:init}
3. 做组件初始化:将我们的虚拟节点转换成真实节点(组件的init方法) new Sub().$mount

17. Vue的组件渲染过程 (init)

  • vm.$options.components[‘my’] = { my: ‘模板’ }
  • 创建组件的虚拟节点 createComponent {tag: ‘my’, data: {hook:{init}}, componentOptions: {Ctor: Vue.extend({my: ‘模板’})}}
  • 创建真实节点的 createComponent init -> new 组件().$mount() -> vm.componentInstance

18. Vue组件更新流程 (prepatch)

  • 组件更新会触发 组件的prepatch方法,会复用组件,并且比较组件的属性 事件 插槽
  • 父组件给子组件传递的属性是(props)响应的,在模板中使用会依赖收集 收集自己的组件watcher
  • 稍后组件更新了 会重新给props赋值,赋值完成后会触发watcher重新更新

19. Vue中异步组件原理

Vue中异步组件的写法有很多,主要用作,大的组件可以异步加载的,markdown组件,editor组件,就是先渲染一个注释标签,等组件加载完毕,最后在重新渲染forceUpdate(图片懒加载) 使用异步组件会配合webpack

20. 函数组件的优势及原理

React中也区分两种组件 一种叫函数式组件(Sub就是类组件,有this) (函数组件 没有类,就是this,也没有所谓的状态,没有生命周期 beforeCreate, created… 好处就是性能好,不需要创建watcher了)

21.Vue组件间传值的方式及之间区别

  • props 父传递数据给子组件 属性的原理就是把解析后的props,验证后就会将属性定义再当前的实例上 vm._props(这个对象上的属性都是通过defineReactive来定义的(都是响应式的)组件再渲染的过程中会去vm上取值 _props属性会被代理到vm上)

  • emit 儿子触发组件更新 在创建虚拟节点的时候将所有的事件 绑定到了listeners,通过 o n 方法绑定事件通过 on方法绑定事件 通过 on方法绑定事件通过emit 方法来触发事件(发布订阅模式)

  • events Bus原来就是 发布订阅模式 $bus = new Vue() 简单的通信可以采用这种方式

  • $parent $children 就是在创建子组件的时候,会将父组件的实例传入。在组件本身初始化的时候会构建组件间的父子关系 p a r e n t 获取父组件的实例,通过 parent获取父组件的实例,通过 parent获取父组件的实例,通过children 可以获取子组件的实例

  • ref 可以获取dom元素和组件的实例 (虚拟没有处理ref,这里无法拿到实例 也无法获取组件)

  • 创建dom的时候如何处理ref的。会将用户所有的dom操作及属性 都维护到一个cbs属性中 cbs(created update insert destory…) 依次调用cbs中create方法。这里就包含ref相关的操作,会操作ref并且赋值

  • provide (在父组件中将属性暴露出来) inject 在后代组件中通过inject属性 在父组件中提供数据,在子组件中递归向上查找

  • $attrs(所有的组件上的属性 不涵盖props) $lisnteners(组件上所有的事件)

  • Vue.observal 可以创造一个全局的对象用于通信 用的也少

  • vuex

22.v-if v-for哪个优先级更高?

function render() {
    with(this) {
        return _c('div', _l((3), function(i) {
            return (flag) ? _c('span') : _e()
        }), 0)
    }
}

v-for的优先级更高,在编译的时候,会将 v-for渲染成_l函数 v-if会变成三元表达式。 v-if和v-for不要在一起中使用

v-if(是否渲染) / v-show(控制的样式 display:none) v-show=“true” 放在span上面会变成块元素嘛
为什么不用 visbility: hidden? 不能响应事件(占位的) 为什么不用 opacity呢? (透明度为0 占位) 可以相应事件的

v-if 在编译的时候,会变成一个三元表达式 v-show在编译的时候变成一个指令

23.v-if, v-model, v-for的实现原理

  • v-if会被编译成三元表达式

  • v-for会被编译成_l 循环 (render-list.js)

  • v-model 放在表单元素上可以实现双向绑定,放在组件上就不一样了
    v-model 放在不同的元素上回编译出不同的结果,针对文本来说会处理文本(会被编译成 value + input + 指令)

    • v-model 绑定到组件上面 这里会编译成一个对象 model对象,组件在创建虚拟节点的时候,会有这个对象。会看这个对象里面的prop和event,如果没有则会被解析成 value+input的语法糖
<input type="input" v-model="msg" />
function render() {
    with(this) {
        return _c('input', {
            // 这里在指令里面会监听中文的输入完毕的事件(compositionstart compositionend)
            // compositionend 方法里面会将composing变成false, 并且手动触发input事件,手动触发
            directives: [{
                name: 'model',
                rawName: 'v-model',
                value: (msg),
                expression: 'msg'
            }],
            attrs: {
                type: 'text'
            },
            domProps: {
                value: (msg)
            },
            on: {
                input: function($event) {
                    if($event.target.componsing) return;
                    msg = $event.target.value
                }
            }
        })
    }
}

24.Vue中slot是如何实现的?什么时候使用它?

<div id="app">
  <my>
    <div>{{msg}}</div>
  </my>
</div>
  //组件my
  new Vue({
    data: {
      msg: 'outer'
    },
    components: {
      my: {
        data() {
          return { msg: 'inner'}
        },
        template: `<div class='my'><slot></slot></div>`
      }
    }
  })

编译父组件

const templateComplier = require('vue-template-compiler')

let result = templateComplier.compile(`<my><div>{{msg}}</div></my>`)

// result被编译成 [_c('div',[_v(_s(msg))])]) 会被立即执行
// _c('my', [_c('div',[_v(_s(msg))])])
1. 编译虚拟节点,生成vnode
//_c 最终编译成
// new Vnode = {'tag': 'my', componentOptions: {children: {tag: 'div', 'hello'}}}
组件的孩子叫插槽,元素的孩子就是孩子
2. 进行组件初始化,创建组件的真实节点
// 进行组件初始化的时候,调用 initInternalComponent方法
function initInternalComponent() {
  ...
  opts._renderChildren = vnodeComponentOptions.children
}
// 创建组件的真实节点, 在slots上面增加属性
function initRender() {
  ...
  this.$slots = resolveSlots(options._renderChildren) // options._renderChildren 这里拿到的是 initInternalComponent 处理过的 _renderChildren
}
function resolveSlots(chilren) {
  for(let i = 0, l = children.length; i < l; i++) {
    const child = children[i]
    slot.defalut.push(child)
  }
}
// this.$slots = [default: [儿子虚拟节点]]
// 将结果做一个映射:this.$scopeSlots = { a:fn, b: fn, defalut: fn }

编译子组件

templateComplier.compile(`<div class="my"><slot><</div>`)
最终会被编译成:
_c('div', {staticClass: 'my'}, [_t('defalut')])
// 组件渲染的时候,会采用组件的模板:_t('defalut'), 在子组件渲染的时候,会通过 _t找到刚才的映射关系进行替换
  • 普通插槽 (普通插槽渲染作用域在父组件中的)

    • 在解析组件的时候会将组件的children 放到 components 上作为虚拟节点的属性
    • 将children取出来放到组件的 vm.$options._renderChildren中
    • 做出一个映射表放到 vm.$slots上 -> 将结果放到 vm.$scopeSlots上 vm.$scopeSlots = { a: fn, b: fn, default: fn}
    • 渲染组件的时候会调用 _t方法,此时会去vm.$scopeSlots找到对应的函数来渲染内容
  • 具名插槽 多增加了名字

  • 作用域插槽 (作用域插槽渲染作用域在子组件中的)

    • 我们渲染插槽选择的作用域是子组件 作用域插槽渲染的时候不会作为children属性,将作用域插槽做成了一个属性scopedSlots
    • 制作一个映射关系 $scopedSlots = {default: fn: function({msg}){return _c(‘div’, {}, [_v(_s(msg))])}}}
    • 稍后渲染组件的模板的时候 会通过name找到对应的函数 将数据传入到函数中此刻才渲染虚拟节点,用这个虚拟节点替换_t(‘defalut’)

25.Vue.use是干什么的?原理是什么?

  • 这里的use方法 目的就是将 vue的构造函数传递给插件中,让所有的插件依赖的Vue是同一个版本
  • 默认调用插件 默认调用插件的install方法

26.Vue事件修饰符有哪些?其实现原理是什么?

  • 实现主要依靠的是模板编译原理 addEventListener(stop, defaultPrevent) self capture poassvie
  • .number

编译的时候直接编辑到事件内部了

  • <div @click.prevent></div>
  • <div @click.stop></div>

编译的时候增加标识 !~&

  • <div @click.passive></div>
  • <div @click.capture></div>
  • <div @click.one></div>

键盘事件

  • 都是通过模板编译来实现的,没有特殊的

27.Vue中.sync修饰符的作用,用法及实现原理

  • 和v-model一样,这个api是为了实现状态同步的,这个东西在vue3中移除了。
<my :xx.sync="info"></my>
function render() {
    with(this) {
        return _c('my', {
            attrs: {
                'xx': info
            },
            on: {
                'update:xx': function($event) {
                    info = $event
                }
            }
        })
    }
}

28.如何理解自定义指令

  • 自定义指令就是用户定义好对应的钩子,当元素在不同的状态时会调用对应的钩子(所有的钩子会被合并到 cbs 对应的方法上,到时候依次调用)

29.keep-alive平时在哪里使用?原理是?

  • 1.keep-alive在路由中使用

  • 2.在component:is 中使用(缓存)

  • keep-alive的原理是默认缓存加载过的组件对应的实例 内部采用LRU算法

  • 下次组件切换加载的时候 此时会找到对应缓存的节点来进行初始化,但是会采用上次缓存$el来触发

  • 更新和销毁会触发 actived 和 deactived

30.组件中写name选项有哪些好处及作用

可以实现递归调用组件

  • 在vue中有name属性的组件可以被递归调用 (在写模板语法的时候,我们可以通过name属性来递归调用自己)
  • 在声明组件的时候 Sub.options.comonents[name] = 组件

起到标识作用

  • 我们用来标识组件, 通过name来找到对应的组件 自己封装跨级通信
  • name属性可以用作devtool调试工具 来标明具体的组件

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

设计模式--外观模式

实验12&#xff1a;外观模式 本次实验属于模仿型实验&#xff0c;通过本次实验学生将掌握以下内容&#xff1a; 1、理解外观模式的动机&#xff0c;掌握该模式的结构&#xff1b; 2、能够利用外观模式解决实际问题。 [实验任务]&#xff1a;计算机开启 在计算机主机(Main…

VSCode中配置prettier和ESLint

文章目录 了解ESLint和Prettier的作用prettier配置ESLint配置常见问答ESLint 和Prettier 有什么区别&#xff1f;为什么我应该同时使用ESLint 和Prettier&#xff1f;在使用ESLint 和Prettier 时&#xff0c;有可能出现它们之间的规则冲突吗&#xff1f;我已经在项目中使用了ES…

微前端——无界wujie

B站课程视频 课程视频 课程课件笔记&#xff1a; 1.微前端 2.无界 现有的微前端框架&#xff1a;iframe、qiankun、Micro-app&#xff08;京东&#xff09;、EMP&#xff08;百度&#xff09;、无届 前置 初始化 新建一个文件夹 1.通过npm i typescript -g安装ts 2.然后可…

软件测试工程师简历项目经验怎么写?--9999个已成功入职的软件测试工程师真实简历

简历是我们求职的第一步&#xff0c;也是非常重要的一步。 青云叔叔看过太多简历&#xff0c;最快3秒就淘汰一份简历&#xff0c;因为其实我们每天要收到很多简历进行筛选&#xff0c;那么面试官其实也是会很快进行对简历进行判断的&#xff0c;如果你对简历写的一塌糊涂&…

8、SpringCloud高频面试题-版本1

1、SpringCloud组件有哪些 SpringCloud 是一系列框架的有序集合。它利用 SpringBoot 的开发便利性巧妙地简化了分布式系统基础设施的开发&#xff0c;如服务发现注册、配置中心、消息总线、负载均衡、断路器、数据监控等&#xff0c;都可以用 SpringBoot 的开发风格做到一键启…

第十三节TypeScript 元组

1、简介 我们知道数组中元素的数据类型一般都是相同的&#xff08;any[]类型的数组可以不同&#xff09;&#xff0c;如果存储的元素类型不同&#xff0c;则需要使用元组。 元组中允许存储不同类型的元素&#xff0c;元组可以作为参数传递给函数。2、创建元组的语法格式&#x…

MATLAB Mobile - 使用预训练网络对手机拍摄的图像进行分类

系列文章目录 前言 此示例说明如何使用深度学习对移动设备摄像头采集的图像进行分类。 在您的移动设备上安装和设置 MATLAB Mobile™。然后&#xff0c;从 MATLAB Mobile 的“设置”登录 MathWorks Cloud。 在您的设备上启动 MATLAB Mobile。 一、在您的设备上安装 MATLAB M…

IDEA控制台乱码

报错情况&#xff1a; 报错原因&#xff1a;Idea的vm用的编码格式不一致&#xff1a;需要修改为UTF-8 你看Tomcat我之前下在后修改果&#xff0c;就没有报错&#xff0c;新人刚下载也有乱码问题 问题解决&#xff1a; 按我步骤来一定对 下面这俩文件打开输入&#xff1a; -D…

医疗机构远程视频监控集中管理,贝锐蒲公英提供一站式解决方案

上海某企业专业致力于医疗软件、家居智能化研发、设计、销售、集成及实施&#xff0c;企业主营业务之一为医疗软件&#xff0c;涉及PACS/RIS/WEB/HIS、示教系统等方面的医院信息化建设。 在实际应用、部署过程中&#xff0c;需要实现各地区分院与总院间的数据库互相访问、视频数…

Portainer.io:让容器管理变得更加直观

在现代软件开发和部署中&#xff0c;容器化技术已经变得越来越流行。Docker 是其中一种领先的容器化平台&#xff0c;而 Portainer.io 则是一个优秀的管理工具&#xff0c;使得 Docker 的使用变得更加简单和可视化。本文将介绍 Portainer.io 的基本功能和如何在 Docker 上安装和…

jQuery: 整理4---创建元素和添加元素

1.创建元素&#xff1a;$("内容") const p "<p>这是一个p标签</p>" console.log(p)console.log($(p)) 2. 添加元素 2.1 前追加子元素 1. 指定元素.prepend(内容) -> 在指定元素的内部的最前面追加内容&#xff0c;内容可以是字符串、…

1-GAN

一、GAN简介 人脸检测、图像识别、语音识别&#xff0c;机器总是在现有事物的基础上做出描述或判断[参考] 能不能创造这个世界不存在的东西&#xff1f;GAN GAN&#xff0c;全称Generative Adversarial Networks&#xff0c;中文叫生成式对抗网络。GAN它包含三个部分&#xf…

【随想】每日两题Day.22

题目&#xff1a;102. 二叉树的层序遍历 给你二叉树的根节点 root &#xff0c;返回其节点值的 层序遍历 。 &#xff08;即逐层地&#xff0c;从左到右访问所有节点&#xff09;。 示例 1&#xff1a; 输入&#xff1a;root [3,9,20,null,null,15,7] 输出&#xff1a;[[3],[…

基于 Editor.js 开发富文本编辑器库

开始 Editor.js 提供了简单而直观的用户界面&#xff0c;根据需求可以灵活添加自定义的编辑工具&#xff0c;通过插件扩展功能 Editorjs 使用 js 开发&#xff0c;脱离框架依赖&#xff0c;因此可以基于它封装富文本编辑器&#xff0c;用于 Vue 和 React 项目 editor-js-com…

C语言、c++实现超好玩植物大战僵尸(完整版附源码)

实现这个游戏需要Easy_X main.cpp //开发日志 //1导入素材 //2实现最开始的游戏场景 //3实现游戏顶部的工具栏 //4实现工具栏里面的游戏卡牌 #define WIN_WIDTH 900 #define WIN_HEIGHT 600 //定义植物类型 enum { WAN_DOU, XIANG_RI_KUI, ZHI_WU_COUNT }; #include<stdio.…

linux系统和网络(三):IO,信号,信号量,线程

本文主要探讨linux的IO,信号,信号量,线程相关知识,详细知识可参考本博客其他文章。 信号&#xff08;可参考本博客其他文章&#xff09; 信号是内容受限的异步通信机制,硬件异常后统内核发出信号 alarm产生SIGALARM信号,读端关闭后管道write产生SIGPIPE信号 常见信号…

2024年起重机司机(限门式起重机)证考试题库及起重机司机(限门式起重机)试题解析

题库来源&#xff1a;安全生产模拟考试一点通公众号小程序 2024年起重机司机(限门式起重机)证考试题库及起重机司机(限门式起重机)试题解析是安全生产模拟考试一点通结合&#xff08;安监局&#xff09;特种作业人员操作证考试大纲和&#xff08;质检局&#xff09;特种设备作…

基于模型驱动的可解释性全色、多光谱、高光谱融合网络

摘要 摘要:同时融合高光谱(HS)、多光谱(MS)和全色(PAN)图像为生成高分辨率HS (HRHS)图像提供了一种新的范式。在这项研究中&#xff0c;我们提出了一个可解释的模型驱动的深度网络&#xff0c;用于HS, MS和PAN图像融合&#xff0c;称为HMPNet。我们首先提出了一种新的融合模型…

编译原理--递归下降分析实验C++

一、实验项目要求 1.实验目的 根据某一文法编制调试递归下降分析程序&#xff0c;以便对任意输入的符号串进行分析。本次实验的目的主要是加深对递归下降分析法的理解。 2.实验要求 对下列文法&#xff0c;用递归下降分析法对任意输入的符号串进行分析&#xff1a; &#…

【并发编程篇】定义最大线程的方法

文章目录 &#x1f354;省流&#x1f3f3;️‍&#x1f308;前言&#x1f6f8;CPU密集型&#x1f339;代码实现 &#x1f6f8;IO密集型 &#x1f354;省流 池的最大大小如何去设置 使用CPU密集型和IO密集型这2种方法 &#x1f3f3;️‍&#x1f308;前言 上一篇文章我们讲解…