/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */
#content_views .toc,
/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */
#content_views.markdown_views > p:empty:has(+ .toc),
#content_views.markdown_views > .toc + p:empty,
/* 富文本旧版目录标记 */
#content_views.htmledit_views #main-toc,
#content_views.htmledit_views #hr-toc,
#content_views.htmledit_views p[id*=\”-toc\”] {
display: none !important;
}
/* 目录去掉后,紧跟的首个标题不再多出一块上边距 */
#content_views.markdown_views > .toc + h1,
#content_views.markdown_views > .toc + h2,
#content_views.markdown_views > .toc + h3,
#content_views.markdown_views > .toc + h4,
#content_views.markdown_views > .toc + p:empty + h1,
#content_views.markdown_views > .toc + p:empty + h2,
#content_views.markdown_views > .toc + p:empty + h3,
#content_views.markdown_views > .toc + p:empty + h4 {
margin-top: 0 !important;
}
写前端代码时,我们经常遇到两种用法:
<script src=\”./xxdemo.js\”></script>
import {
hello } from \’./xxdemo.js\’
同样是 JS 文件,为什么加载方式不同?为什么有些库会写 window.xxx,有些库却使用 export?IIFE 又是什么,为什么要让函数定义后立即执行?
1. JS、TS、ESM、npm,分别在说什么?
先分清它们描述的层面:
| JavaScript,简称 JS | 编程语言 | 编写浏览器执行的逻辑 |
| TypeScript,简称 TS | 带类型系统的语言 | 开发时增加类型检查,通常转换为 JS 后交付 |
| ESM | JavaScript 的标准模块机制 | 用 import 和 export 共享功能 |
| IIFE | 一种函数表达式写法 | 函数定义后立即调用,常用于隔离内部变量 |
| npm | 软件包管理和分发 | 安装依赖、管理版本、发布代码包 |
| Vite、esbuild 等 | 开发和构建工具 | 转换源码、处理依赖、生成发布文件 |
因此,“使用 JS 还是 ESM”并不是两个并列选项。采用 ESM 时,写的仍然可以是 JavaScript。
TypeScript 的类型主要在开发阶段帮助检查代码,不会作为类型检查逻辑自动带到浏览器中。参考:TypeScript 官方入门
2. 普通 script 是怎么使用 JS 的?
本文把没有 type=\”module\” 的 JavaScript 脚本称为“普通脚本”,也叫经典脚本。
例如,一个完整的 HTML 页面可以这样写:
<!DOCTYPE html>
<html lang=\”zh-CN\”>
<head>
<meta charset=\”UTF-8\”>
<title>xxdemo 普通脚本示例</title>
</head>
<body>
<p id=\”output\”></p>
<script>
function hello(name) {
return \’你好,\’ + name
}
document.getElementById(\’output\’).textContent = hello(\’xxdemo\’)
</script>
</body>
</html>
这里的代码由浏览器直接执行。也可以把脚本移到外部文件,再通过 src 加载。
文件以 .js 结尾,并不能说明它是普通脚本还是 ESM。 还要看文件内容,以及它被怎样加载。参考:MDN script 元素
3. window.xxx 是什么?
在浏览器页面里,window 是全局对象。下面的代码给它增加了一个属性:
window.XXDemo = {
hello(name) {
return \’你好,\’ + name
}
}
其他脚本就可以使用:
window.XXDemo.hello(\’xxdemo\’)
在没有同名局部变量遮蔽等情况下,也可以写:
XXDemo.hello(\’xxdemo\’)
把功能集中在 XXDemo 下面,可以避免将许多名字分别放到全局,例如 window.hello、window.reset、window.start。
但 window.xxx 本身不是模块规范。普通脚本可以给它赋值,ESM 也可以给它赋值。
4. IIFE 为什么要立即执行?
IIFE 的全称是 Immediately Invoked Function Expression,中文叫“立即执行函数表达式”。
普通函数往往先定义,再调用:
function start() {
console.
网硕互联帮助中心


评论前必须登录!
注册