Vue.js系列:对象的变化侦测
对于对象属性的变化侦测,是vue响应式的核心。其本质需要实现的功能:当改变对象某属性值的时候,我们需要捕捉到这个变化。那么vue是怎么做到的?defineProperty
前端目前三大框架三分天下,实现响应式的方式却各有不同。angular、react属于”pull(拉)“,而vue则属于”push(推)“。两者的区别在于,拉的方式是被动的,推的方式则是主动的。当我们改变了某个对象的某个值之后,对于前者而言,框架能够知道,某些状态发生了变化但是不知道具体谁发生了变化,所以此时会暴力的对比找出变化的状态,而对于后者而言,当属性值改变后,会把这个改变了的状态主动告诉框架。然后框架去通知这个状态的所有依赖。这就是为什么vue的响应式被称之为“细粒度”的响应式。
具体实现:
const definePropertyReactive = (obj, key, val) => {
Object.defineProperty(obj, key, {
get() {
console.log('val>>', val)
return va ...
Vue.js系列:序章
毕业到现在快两年了,职业生涯中的项目基本都是基于vue2开发的。一直以来,注重的都是业务功能的实现,却很少关注其底层的逻辑特性。从本文开始,我会通过手头的资料,对vue2以及vue3,做一些备忘录,重点记录下其实现的基本逻辑,以及自己对其的思考。同时,因为我们也都知道,vue2.0版本,将于本年年底,也就是2023年的12月份停止维护,也算是个人对其的一个致敬吧。
vue这种框架出现的结果,就是将以前jquery那样的命令式操作dom的方式—>声明式的操作dom,翻译成人话就是:数据驱动视图,数据变,视图自动的变。同时视图由于用户的操作变化,也会更新数据。至于怎么生成节点插入节点等dom操作,不再关心,也无需关心。
举例说明:
<!DOCTYPE html>
<html lang="en">
<head>
<title>Document</title>
</head>
<body>
<button id="add">+</button>
<button id="sub">-</button> ...
JS的转折分界: ES6
不管有没有系统的去学习ES6相关的概念,但我相信,在日常开发中,都或多或少的使用到了相关方法。笔者一直很纳闷,事实上ES6从发布至今也蛮长时间了,但是面试的时候总会有面试官问这么个问题:ES6有什么新的特性。。。。事实上这是因为该版本,对于js这门语言而言,具有里程碑的意义.那么本文尝试着将最重大的改动梳理梳理.
首当其冲的必定是let、const块级作用域声明方式。同var相比两个不同。块级作用域能够屏蔽var的变量提升,将变量的生命周期局限在块中。本质讲,var所谓的变量提升指的是用其声明的变量,会自动提升到作用域的顶部。const f = function () {
if (false) {
let name = '1234'
//var name = '1234'
}
console.log('name:', name)
}
f()
用var声明的name,打印是undefined,而用let打印的是not defined,error
模板字面量。简单地讲,就是可以在字符串 ...
谷歌插件流程:第二回
在前文中,我们通过一个小例子,简单介绍了谷歌插件的一些规则。那么本文正式尝试着,去实现自己的视频下载器插件的开发。目的:能够自动下载知乎上的短视频资源。古语云:知己知彼百战不殆。那么我们首先就去看一看知乎站点的小视频资源是如何加载的。
我们发现,video的src属性绑定的是真实的资源地址,也就是说,我们只需要找到video标签即可。思路: 进入到目标tab页面的环境,获取video标签,创建a标签下载.所以有了如下代码:
changeColor.addEventListener("click", async () => {
console.log('click')
let [tab] = await chrome.tabs.query({ active: true, currentWindow: true });
chrome.scripting.executeScript({
target: { tabId: tab.id },
function: downloadVideo,
} ...
谷歌插件流程:第一回
相信经常使用chrome的小伙伴们,对其丰富的插件工具不会陌生。比如下载页面视频、音乐等等等。那么这些工具究竟是如何编写的呢?本文将以谷歌官方实例为基础,简单介绍一下chrome插件的开发流程,我们最终的目标,是写一个自己的视频下载器插件。部分内容参考下面地址文章
http://runxinzhi.com/wintertone-p-12053751.html
1. 第一步创建一个空的文件夹,后创建manifest.json文件,可以理解为整个插件的名片,代码如下。{
"name": "Ta-da",
"description": "download_zhihu_short_video",
"version": "1.0",
"manifest_version": 3,
"background": {
"service_worker": "background.js"
},
"permissions": ["storage", "activeTab", "scripting"],
"action": {
...
性能的考量:第四回(代码层面)
本文从代码层面出发,介绍一些小技巧以提升性能古语有云,千里之堤,溃于蚁穴,性能的问题如出一辙。尤其是在图形化编程的项目中,日积月累的烂代码,导致最终页面的不堪重负。而此时,却束手无策,只能大量重构。因此,在写每一行代码的时候,都应该对性能有所考虑。
1.HTML、JS、CSS三者解耦,各司其职html是数据,js是行为,css负责外观。三者代表了三个层面,应该各司其职互不干扰.如下代码:
const dom = document.getElementById('id')
dom.style.height = 100 + 'px'
dom.style.width = 100 + 'px'
css才应该负责样式层,所以任何的样式问题都应该通过css文件解决。而上述代码则是js承担了页面显示的任务。造成js和css的耦合。但是这种需求有时候不可避免,我们可以使用替代方案,降低耦合度:
const dom = document.getElementById('id')
dom.className = 'dddd'
通过设置类名的方式,达到我们目的的同时,还能保持css负责显示的底线。
2.事件 ...
性能的考量:第三回(canvas)
本文主介绍canvas的性能优化策略关于性能问题,实际上,针对于类似管理系统这样的项目而言,不需要关注太多,也没那必要.但是对于图形编程类的项目而言,则是至关重要的指标.关乎生死。
先点名canvas的耗时因素
图形的数量
图形的大小。
高质量、大文件的图片(画在画布上)
图形编程类的项目,关注性能问题的原因,在于交互体验。比如我们废了半天劲写了一个web端的类cs射击游戏,当我兴奋的准备往前走两步时,发现页面直接给我来了个帧数级别的慢动作,江湖说法叫做”卡成狗”,用户体验几乎为0。这种完全不能玩的应用,如同垃圾。
我们首先来定义一下, 什么叫做卡?卡顿原理可以解释为,每一帧js主线程执行的事情过多,导致帧内时间没来得及干完,即当前帧耗时超过分配的帧时间。那么什么是”分配的帧时间?60hz举例,一秒钟60帧,那么一帧的时间大约在16.7ms.所以,如果在一帧内的耗时超过了16.7ms,就会出现视觉层面的”卡”。目前主流的屏幕基本都是60hz,也就是显示器,以每秒60次的频率闪频,但我们人眼无法察觉。
在实践的项目中,我们遇到了一个这样的警告:白话就是,“大哥,您在一帧时间内做的事情太 ...
性能的考量:第二回(工具篇)
本文主要是介绍一些实用的性能相关的工具1. 工具traceroute我们都知道请求会通过不止一台路由器去跳转,直到找到最终的目标ip服务器。那么这个工具能够帮助你查看个中的细节。
2. performance对象运行一个前端项目,除了通过开发者工具中的memory组件,查看内存使用情况,实质上浏览器也提供了api。
通过window的performance属性,我们能够看到一些陌生的字段。包含memory、navigation、timing和eventCounts。
memory字段。很显然,就是我们想看的内存的大小。usedJSHeapSize表示:JS 对象占用的内存数。totalJSHeapSize表示:可使用的内存大小。jsHeapSizeLimit表示:内存大小限制。通常,usedJSHeapSize不能大于totalJSHeapSize,如果大于,有可能出现了内存泄漏。
利用这个api可以做一个页面性能的监控器
3. 工具curl,测试目标域的响应 curl www.baidu.com
<!DOCTYPE html>
<!--STATUS OK- ...
性能的考量:第一回(方法篇)
本文旨在梳理目下通用的性能优化方法性能优化没有一个统一的指标,但目的是明确的,就是要让站点应用的加载速度够快,如此用户体验才能高(暂且不管页面做的烂不烂),毕竟从应用开发者的角度看,时间就是金钱。为了让时间压缩到极致,我们需要从请求到完全响应的全部细节入手,尽可能的压缩。即:从用户在地址栏中输入—>页面加载完成,该过程中的每一个点,都需要倍加注意。可能这就是为什么那么多面试官那么喜欢问一道烂大街的题: 地址栏里输入地址后到直到页面展示,尽可能详细地说说…
精髓部分根据《高性能浏览器网络》的研究结论得出,性能优化三个大的角度:带宽、延时和渲染耗时.那么由于现代光纤通信的大规模普及,带宽的影响因素,已经小到可以忽略不计的地步(管道宽到你怎么都塞不满),所以本文不讨论,剩下的就是延时和渲染。
延迟耗时层面《计算机网络》的第六版中,对于延迟给出了明确的定义,从c端发出消息到s端收到消息的时间消耗,具体包括:排队延迟 –(缓冲)-> 处理延迟–(路由)->传输延迟—>传播延迟。但是扯了这么多是基于一个大前提的,就是真实发送请求的情况下。引用《高性能浏览器网络》的终极解决 ...
设计模式:单例模式
所谓单例模式,就是保证类的实例只有一个。思路很清晰,就是在构造函数中置一个标志,或者已存在的实例对象。先来一道简单版:**const f = function(name) {
this.single = null
this.name =name
}
f.getObj = function(name) {
if(!this.single) {
this.single = new f(name)
return this.single
} else {
return this.single
}
}
const a = f.getObj('s1')
const b = f.getObj('s2')
console.log(a)
console.log(b)
// f { single: null, name: 's1' }
// f { single: null, name: 's1' }
这种实现方式其实很简单,实际上就是 ...
