前端开发之性能优化

本文章 对各大学习技术论坛知识点,进行总结、归纳自用学习,共勉🙏

文章目录

1. CDN

CDN(内容分发网络)是一种基于互联网的分布式服务,旨在通过将网站内容分发至全球多个节点,来提高用户访问速度和可靠性。广泛适用于各类静态和动态内容,包括网页文件、图片、视频、应用程序等。CDN的核心目标是减少数据传输距离和网络拥堵,从而加快内容加载时间,提升用户体验。

  • 内容缓存 :将网站的静态资源复制并存储在全球各地的CDN节点上,用户请求时,CDN会将内容从距离用户最近的节点提供,减少延迟。
  • 负载均衡 :通过智能调度算法,CDN能够根据网络状况、服务器负载等因素,将用户请求分配给最适合的节点,平衡各服务器的访问压力。
  • 故障容错 :当某个CDN节点出现问题时,系统会自动将流量导向其他健康节点,确保服务的连续性和稳定性,减少单点故障的影响。
  • 动态内容加速:除了静态资源,现代CDN还支持动态内容的加速,通过优化网络路径和减少往返时间,提高如API请求、数据库查询等动态内容的响应速度。、

CDN的使用场景:

  • 使用第三方的CDN服务:使用开源一些项目、插件、组件,即用即CDN服务
  • 静态资源缓存加速网站性能 :对于任何网站而言,将静态资源JavaScript、CSS、图片等托管于CDN上,可以显著加速页面加载速度。由于这些资源往往不经常变化,通过CDN分发,用户能从距离最近的节点加载数据,减少延迟,提高用户体验。同时,将整个项目部署在CDN上,可以实现快速、简便的一键部署,便于维护和版本更新。
  • 直播服务的流媒体传输 :在直播场景中,CDN扮演着至关重要的角色。由于直播内容是实时、连续的数据流,传统的静态资源缓存策略不再适用。CDN针对流媒体设计了特殊的传输机制,通常采用主动推送技术,确保数据连续、低延迟地传输到用户端。这种方式避免了因回源请求大流量数据造成的网络拥塞和延迟,确保了直播画面的流畅与即时性,提升了观众的观看体验。
  • 大文件下载和软件分发 :对于需要提供大文件下载的场景,如游戏客户端、软件更新包、大型文档等,CDN可以有效分担主服务器压力,提供快速下载通道,确保用户在全球各地都能获得高速下载体验。
  • 电商与广告平台 :在电商节或促销活动期间,网站面临巨大流量冲击,CDN能够有效分散访问压力,保证页面快速加载,提升转化率。同时,广告平台通过CDN快速分发广告素材,确保广告加载迅速,提升广告展示效率。

2.懒加载

懒加载也是一种性能优化技术,特别适合图片或多媒体内容丰富的页面,通过延迟加载那些暂时不在视窗内(即用户当前屏幕看不到的内容)的资源,来减少初次加载时的请求数量和数据量,从而加快页面的初始加载速度,提升用户体验。

👉图片懒加载

3.缓存

缓存作为提升系统性能的关键技术之一,其核心思想在于通过存储最近或经常访问的数据副本,减少对原始数据源的访问次数,从而达到加速数据读取、降低系统响应时间和负载的目的。耳缓存原理就是更快读写的存储介质+减少IO+减少CPU计算=性能优化 。而性能优化的第一定律就是:优先考虑使用缓存

缓存的主要手段有:浏览器缓存、CDN、反向代理、本地缓存、分布式缓存、数据库缓存。

4.图片压缩

图片压缩对于优化网站性能、加快页面加载速度至关重要,特别是在移动设备和有限带宽的网络环境下。
用工具开压:

  • Squoosh:这是一个开源的在线图片压缩工具,支持各种格式(包括WebP、JPEG、PNG等),特点是用户界面友好,可以实时预览压缩效果,并允许手动调整压缩级别,直至达到满意的效果。

  • CompressJPEGCompressPNG :这两个网站分别专注于JPEG和PNG格式的图片压缩,操作简单,上传图片后即可快速压缩,适合一次性处理少量图片。

  • ImageOptim(Mac)/ FileOptimizer(Windows):这两款是桌面端的图片优化工具,支持拖拽操作,可以批量处理图片,自动应用最佳压缩算法,无需用户手动调整。

  • Adobe Photoshop:ps有图片压缩和导出功能。可以使用其"Save for Web"或"Export As"功能来优化图片大小,同时保持较好的质量。

  • 再不济就找UI压缩

5.图片分割

比如一张效果图,UI又开始乱叫不愿意压缩,它喵的,真是小刀拉屁股,那就割。

思路:

  1. 使用工具分割图片: 首先,需要使用像Photoshop、GIMP这样的图像编辑软件,或者自动化脚本(如Python的PIL库)将大图切割成多个小图。假设我们决定将图片分割为4个部分,每个部分大小适中,建议不超过100KB
  2. 命名与组织: 分割后,确保每个图片文件命名有序,便于后续引用,例如:image_part_1.png, image_part_2.png, image_part_3.png, image_part_4.png

接下来,我们将使用HTMLCSS来展示如何将这些图片按原顺序拼接起来。请注意,为了防止图片加载时导致布局错乱,我们为每个图片分配了固定高度。

html 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>图片分割示例</title>
<style>
    .image-container {
        display: flex;
        flex-wrap: nowrap;
        width: /* 原图片总宽度 */;
        height: /* 原图片总高度的一半,因为是两行两列布局 */;
    }
    .image-part {
        width: /* 原图片宽度的一半 */;
        height: /* 原图片高度的一半 */;
        object-fit: cover; /* 保持图片比例并填充容器 */
    }
</style>
</head>
<body>

<div class="image-container">
    <img src="image_part_1.png" class="image-part" alt="图片分割1">
    <img src="image_part_2.png" class="image-part" alt="图片分割2">
    <img src="image_part_3.png" class="image-part" alt="图片分割3">
    <img src="image_part_4.png" class="image-part" alt="图片分割4">
</div>

</body>
</html>

请根据实际情况调整CSS中的宽度和高度值,以匹配原始图片的尺寸和分割后图片的实际大小。同时,确保所有分割图片的路径是正确的。

6.sprite

精灵图(Sprite),在网页开发中确实扮演着重要角色,尤其是在优化网站性能方面。

通过将多个小图标合并成一张大图,减少HTTP请求、减轻服务器负担、加快页面渲染、优化缓存利用及减少带宽消耗,成为了提高网页性能的有效手段。尽管随着HTTP/2协议的普及和新的技术如SVG图标、Icon Fonts以及CSS Sprites inlining的出现,精灵图的使用场景有所减少,但在特定场景下,尤其是针对小图标和背景图的优化,它仍然是一个有价值的解决方案

7.Code Splitting

Webpack代码分割是优化前端应用加载速度的关键技术之一。Webpack 4 及以上版本默认开启了动态代码拆分,它会自动将较大的代码块分离成不同的chunk(或称为bundle),以实现按需加载,进而提升用户体验。
Webpack 4 默认分包策略 不进行任何特殊配置,Webpack 4 就能执行以下操作:

  • 入口文件依赖 :所有直接或间接由入口文件引用的模块会被打包进main.js(或其他命名的主输出文件)。
  • 第三方库分 离:大于30KB的第三方库(如echarts、xlsx等)会被单独打包成chunk,这样它们可以被缓存并在不同页面间复用,减少重复下载。
  • 异步加载组件 :使用动态导入(如import())的模块会自动生成独立的chunk,实现懒加载。
  • 并发限制 :初始加载时,Webpack会控制并发请求数量不超过一定限制,以避免过多请求导致的性能问题。

splitChunks示例细化分包更改配置:

javascript 复制代码
splitChunks({
  cacheGroups: {
    vendors: {
      name: `chunk-vendors`,
      test: /[\\/]node_modules[\\/]/,
      priority: -10,
      chunks: 'initial',
    },
    dll: {
      name: `chunk-dll`,
      test: /[\\/]bizcharts|[\\/]\@antv[\\/]data-set/,
      priority: 15,
      chunks: 'all',
      reuseExistingChunk: true
    },
    common: {
      name: `chunk-common`,
      minChunks: 2,
      priority: -20,
      chunks: 'all',
      reuseExistingChunk: true
    },
  }
})

按需加载

即使在未使用Webpack 4的项目中,也可以通过一些策略实现按需加载,例如使用动态导入(import()表达式)、CommonsChunkPlugin(在Webpack 4之前的版本中)或手动分割代码到不同的entry点,以此来减小初始加载包的大小,提升应用加载速度。👉 webpack如何使用按需加载

8.gzip

gzip是一种广泛应用于Web服务器和客户端之间的数据压缩传输技术。通过在服务器端对响应内容进行压缩,然后由客户端解压,可以显著减少通过网络传输的数据量,从而加快页面加载速度,降低带宽消耗。

javascript 复制代码
http {
  # 开启gzip压缩
  gzip on;

  # 设置用于压缩的缓冲区数量和大小,这里是32个4K的缓冲区
  gzip_buffers 32 4K;

  # 设置压缩级别,范围为1-9,数字越大压缩程度越高,消耗CPU资源也越多。这里设置为6,是比较均衡的设置。
  gzip_comp_level 6;

  # 设置最小压缩长度,只有响应内容长度大于此值时才会进行压缩。这里设置为100字节。
  gzip_min_length 100;

  # 指定可以进行gzip压缩的MIME类型。这里包含了常见的文本和脚本类型。
  gzip_types application/javascript text/css text/xml;

  # 禁用特定版本的IE浏览器的gzip压缩支持,避免一些老版本IE的兼容性问题。
  gzip_disable "MSIE [1-6]\.";

  # 启用`Vary: Accept-Encoding`响应头,让代理服务器知道缓存需要区分是否支持gzip的请求。
  gzip_vary on;
}

这段配置放置在Nginx的配置文件(通常是nginx.conf)中的http内,它告诉Nginx对符合规则的HTTP响应启用gzip压缩。通过调整这些参数,可以优化压缩效果以适应不同的服务器环境和性能需求。例如,gzip_comp_level可以根据服务器的处理能力适当调整,以平衡压缩效率和CPU负载;gzip_types可以按需添加更多的MIME类型以覆盖更多种类的资源。

启用gzip压缩后,务必确保服务器和客户端(浏览器)都支持并开启了gzip解压功能,这样才能充分利用这一优化措施。

9.GPU加速

利用GPU(图形处理器)来渲染复杂的CSS动画和其他图形密集型任务可以显著提升网页性能。现代浏览器通过硬件加速技术,能够将部分图形处理工作从CPU转移到GPU上,从而减轻CPU负担,尤其是在处理大量像素操作和动画时更为高效。

绝大部分主流浏览器都支持GPU加速,通过某些CSS属性来提示浏览器对特定元素使用GPU加速,尽管直接的3D变换(如rotate3d, translate3d)会自然触发硬件加速,但有时候即便不需要实际的3D效果,也可以"欺骗"浏览器开启GPU加速,比如使用:

javascript 复制代码
.element {
  transform: translateZ(0);
  /* 或者 */
  transform: translate3d(0,0,0);
}

这两个属性都能暗示浏览器为该元素创建一个新的复合图层,并尝试使用GPU进行渲染。注意,translateZ(0)实际上并没有改变元素的位置,但它足以触发硬件加速机制。

总之,GPU加速是提升网页动态效果和交互流畅度的有效手段,但关键在于理解和合理应用,确保在提升用户体验的同时,保持良好的性能表现。

10.Ajax

Ajax 可以利用浏览器的缓存机制来提高响应速度和提升用户体验,但这主要取决于请求的类型(GET vs POST)以及服务器端设置的缓存控制头信息。下面是一些关键点:

  • 默认缓存行为:浏览器通常会对GET类型的Ajax请求进行一定程度的缓存,尤其是当请求的URL包含相同的查询字符串时。这意味着,如果发送了一个之前已经请求过的、具有相同URLGET请求,浏览器可能会直接从本地缓存中返回结果,而不是再次向服务器发起请求。这对于获取静态数据或很少变化的数据非常有用。
  • 控制缓存:服务器可以通过HTTP响应头来控制GET请求的缓存行为,比如使用Cache-Control、Expires等头部字段来指定资源的最大缓存时间或缓存策略。开发人员也可以通过JavaScript设置Ajax请求的cache选项来覆盖浏览器的默认行为。例如,在jQuery中,可以设置cache: false来强制每次请求都从服务器获取新数据。
  • 对于POST请求,浏览器默认行为一般是不进行缓存的,因为POST通常用于提交数据到服务器,这些数据应该是有状态的,每次请求应当产生不同的结果。尽管可以通过特定的HTTP头来指示缓存POST请求,但这并不常见,且可能违反RESTful原则和用户的预期

使用缓存的策略:

  1. 明确缓存策略:根据数据的性质(是否经常更新,是否敏感)来决定是否启用缓存以及缓存多久。
  2. 版本控制:为避免因缓存导致用户无法获取到最新数据,可以在请求的URL中加入版本号或时间戳作为查询参数,即使内容未变,URL的变化也会促使浏览器重新请求。
  3. 使用ETag或Last-Modified:这些HTTP头部可以用来验证缓存数据的有效性,只有当服务器上的数据发生改变时,才需要重新下载。

总之Ajax确实可以通过利用浏览器缓存来提高页面响应速度,但重要的是要理解不同HTTP方法的缓存特性,并根据实际应用场景合理配置缓存策略,以平衡数据的实时性与性能优化的需求。

11.Tree Shaking

摇树(Tree Shaking)是现代前端打包工具(如Webpack、Rollup等)中的一种优化技术,旨在消除未使用的代码,以减小最终生成的JavaScript文件体积。这个术语形象地比喻为从代码"树"中摇掉未被触碰的"叶子"(即未引用的代码),留下仅包含实际使用功能的最小化代码。

摇树优化主要依赖于ES模块(ESM,ECMAScript Modules)的静态导入导出特性。在ESM中,由于导入导出关系在编译时就可以确定,打包工具可以分析哪些导出的模块或函数没有被其他模块直接或间接引用,进而将这部分未被引用的代码从最终的打包产物中移除。

  • 使用ES模块: 确保项目使用ES模块(.mjs在package.json中设置"type": "module")。
  • 明确的导出: 第三方库或你自己的代码需要使用明确的导出(如export)而非默认导出(export default),因为明确导出更便于工具静态分析。
  • 生产环境配置: 在Webpack 4及以上版本,摇树优化默认开启,但通常在生产环境配置中通过设置如mode: 'production'来确保最佳优化。
  • 模块化第三方库: 使用支持摇树优化的第三方库,这些库需要使用ES模块且正确标记了侧效应(side-effects)。未标记有副作用的库可能会导致无效的摇树优化。

在Webpack配置中,开启摇树优化通常意味着:

javascript 复制代码
// webpack.config.js
module.exports = {
  mode: 'production', // 生产模式自动开启摇树优化
  module: {
    rules: [
      {
        test: /\.m?js$/,
        exclude: /(node_modules|bower_components)/, // 排除某些大型库或不希望进行摇树优化的模块
        use: {
          loader: 'babel-loader',
          options: {
            presets: ['@babel/preset-env'],
          },
        },
      },
    ],
  },
};
  • 不是所有场景都能完美实现摇树优化。例如,使用动态导入(import())或在代码中存在全局副作用(如修改全局变量或执行副作用的IIFE)时,可能会影响摇树的效果。
  • 对于一些库来说,即便使用了明确的导入方式,如果没有正确的package.json配置(比如缺少"sideEffects"字段),也可能导致摇树不彻底。

总之,摇树是一种强大的优化手段,但它的效果依赖于代码的编写方式和配置的合理性。合理利用这一技术,可以显著减小应用的体积,加快加载速度,提升用户体验。

12.Resource Hints

Resource Hints 是一种强大的性能优化策略,它允许开发者通过提供有关页面加载所需资源的线索,帮助浏览器提前加载或建立连接,从而减少资源加载延迟,提升用户体验

  1. <link rel="dns-prefetch"> :预先解析DNS查询,减少域名解析时间。当浏览器遇到这个提示时,会立即开始DNS查找,即使该资源还未被请求。适用于那些即将被使用的外部资源的域名。
  2. <link rel="preconnect">:在实际请求资源之前,预先建立与目标服务器的连接(包括DNS查找、TCP握手、TLS协商等)。这对于需要跨域的资源尤其有用,因为它可以减少往返时间。
  3. <link rel="prefetch">:提示浏览器预加载可能在未来需要的资源,但优先级低于当前页面需要的资源。这适用于可能在用户导航至其他页面时用到的资源,比如预加载下一页的内容。
  4. <link rel="preload">:指示浏览器立即加载指定资源,且优先级较高,保证这些资源在页面需要时能够立即可用。适用于关键路径资源,如首屏渲染所需的CSSJavaScript文件。
  5. <link rel="subresource">:与preload相似,用来指示浏览器提前加载对当前页面渲染至关重要的子资源。不过,subresource已被废弃,推荐使用preload代替。
  6. <link rel="prerender">:预渲染整个页面,将其加载到内存中并准备渲染,但不直接展示给用户。当用户导航到该页面时,可以实现瞬间加载。适用于用户很可能会访问的下一个页面。
  7. 本地存储(如localStorage ):虽然严格来说不属于Resource Hints的范畴,但通过本地存储(如localStorage或IndexedDB)缓存资源信息或数据,可以在用户再次访问时快速恢复,达到类似预加载的效果。

通过合理使用这些Resource Hints,开发者能够显著提升网页的加载速度和响应性,但需注意不要过度预加载,以免增加不必要的网络流量和占用用户设备资源。优化时,应结合用户行为分析和性能监控数据,做出最合适的决策。

相关推荐
王解1 小时前
webpack loader全解析,从入门到精通(10)
前端·webpack·node.js
老码沉思录1 小时前
写给初学者的React Native 全栈开发实战班
javascript·react native·react.js
我不当帕鲁谁当帕鲁1 小时前
arcgis for js实现FeatureLayer图层弹窗展示所有field字段
前端·javascript·arcgis
那一抹阳光多灿烂1 小时前
工程化实战内功修炼测试题
前端·javascript
放逐者-保持本心,方可放逐2 小时前
微信小程序=》基础=》常见问题=》性能总结
前端·微信小程序·小程序·前端框架
毋若成4 小时前
前端三大组件之CSS,三大选择器,游戏网页仿写
前端·css
红中马喽4 小时前
JS学习日记(webAPI—DOM)
开发语言·前端·javascript·笔记·vscode·学习
Black蜡笔小新5 小时前
网页直播/点播播放器EasyPlayer.js播放器OffscreenCanvas这个特性是否需要特殊的环境和硬件支持
前端·javascript·html
秦jh_6 小时前
【Linux】多线程(概念,控制)
linux·运维·前端
_乐无6 小时前
Unity 性能优化方案
unity·性能优化·游戏引擎