谷粒商城实战笔记-29~34-前端基础 - ES6
文章目录
- 零,安装Live Server插件
- 一,创建前端工程
- 1,创建工程
- 2,在工程ES6中创建一个html文件
- 二,ES6 简介
- 1,ES6 的历史
- 三,前端基础ES6
- 1,let 和 const
- 1.1,let
- 1.1.1 严格的作用域限制
- 1.1.2 同名变量的重复声明
- 1.1.3,作用域提升
- 1.2,const
- 2,解构
- 2.1 数组解构
- 2.2 对象解构
- 3,字符串
- 3.1 插值字符串
- 3.2 Unicode 支持增强
- 3.3 遍历器接口(Iterator Protocol)
- 3.4 新的字符串方法
- 3.5 `normalize()` 方法
- 3.6 多行字符串
- 3.6.1 创建多行字符串
- 3.6.2 保留或移除空白
- 4,函数新特性
- 4.1 参数默认值
- 4.2 不定参数
- 4.3 箭头函数
- 4.3.1 声明箭头函数
- 4.3.2 箭头函数结合解构表达式
- 5,数组的Map和Reduce方法
- 5.1 map() 方法
- 5.2 reduce() 方法
- 语法:
- 示例:
- 6,Promise
- 6.1 场景说明
- 6.2 回调地狱-传统实现
- 6.3 使用Promise重构
- 6.3.1 Promise 语法
- 6.3.2 用Promise实现上述需求
这一节学习创建前端工程、ES6语法,主要是let和const的使用。
零,安装Live Server插件
为了方便测试,请先给VSCode安装Live Server插件。
有了这个插件后,在VSCode的编辑界面,右键选择Open With Live Server
可以快速部署前端服务,自动打开浏览器访问当前html文件。
一,创建前端工程
1,创建工程
我们创建一个新的前端工程,用于前端知识的学习。
打开VSCode,选择File->Open Folder
。
在打开的窗口中创建并选择文件夹ES6。
2,在工程ES6中创建一个html文件
选择File->New File
。
创建一个名为let.html
的文件。
使用快捷键Shift+!
,快速生成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>
</head>
<body></body>
</html>
二,ES6 简介
ECMAScript 6,通常被称为ES6,是JavaScript的一种规范,于2015年发布,因此有时也被称为ES2015。它是JavaScript语言的一次重大升级,引入了一系列新特性和语法糖,旨在提高语言的性能、可读性和功能丰富度。ES6 的目标之一是让JavaScript更接近其他成熟的编程语言,同时也保持其原有的灵活性和动态性。
1,ES6 的历史
JavaScript 作为一种脚本语言,最初由网景公司(Netscape)的布兰登·艾奇(Brendan Eich)在1995年用10天时间创造出来,旨在为网页添加动态效果。随着时间的推移,JavaScript 不断发展,逐渐成为一种全栈开发语言,不仅限于浏览器端,还被广泛应用于服务器端(如Node.js)、移动应用开发(如React Native)等场景。
三,前端基础ES6
1,let 和 const
在ES6之前,JavaScript中唯一的变量声明关键字是var
。
然而,var
存在一些问题,比如变量提升(hoisting)和作用域链的问题,这可能导致意料之外的行为。
为了解决这些问题,ES6引入了let
和const
关键字,提供了块级作用域和更安全的变量声明方式。
1.1,let
1.1.1 严格的作用域限制
let
声明的变量,只能在其所在的作用域内使用,不能在作用域外使用。关于作用域,可以理解为一对大括号内。
代码示例:
{var a = 1// 作用域限制,只能在大括号内使用,否则会报错let b = 2;}console.log("a="+a)console.log("b="+b) // Uncaught ReferenceError: b is not defined
1.1.2 同名变量的重复声明
let
声明的变量,同名变量只能被声明一次,var可以多次声明同一个变量。
{var a = 1;var a = 'xxx';let b = 2;let b = 3;}
let对变量b的重复声明,编译不通过。
1.1.3,作用域提升
let声明的变量,必须先声明后使用。var声明的变量,可以先试用,后声明。也就是说var声明的变量会在编译时提升到代码的最前面。
{console.log("a="+a)console.log("b="+b) // let.html:14 Uncaught ReferenceError: Cannot access 'b' before initializationvar a = 1;var a = 'xxx';let b = 2;
}
1.2,const
const
关键字用于声明常量,即一旦赋值就不能再改变的变量。这有助于防止意外的修改,从而减少bug。
代码示例:
const PI = 3.14159;
// PI = 3; // 这行代码会抛出错误,因为不能给const声明的变量重新赋值console.log(PI); // 输出:3.14159
值得注意的是,虽然const
变量本身不可重新赋值,但如果是引用类型(如对象或数组),则其内部的属性或元素是可以修改的。
代码示例:
const person = { name: "Alice" };
person.name = "Bob"; // 修改对象内的属性是允许的
console.log(person.name); // 输出:"Bob"
通过使用let
和const
,可以写出更清晰、更安全的代码,这在构建复杂的前端应用时尤其重。
2,解构
解构赋值是一种新的赋值语法,它允许你按照预先确定的模式,从数组、对象中抽取值,然后对变量进行赋值。
2.1 数组解构
下面代码中,定义了一个数组,要从数组中取出元素,可以采用如下方式。
{let arr = [1,2,3];let a = arr[0];let b = arr[1];let c = arr[2];console.log('a='+a);console.log('b='+c);console.log('c='+c);}
上面的代码有很多冗余,ES6提供了一种新的语法,更简洁易用。
{let arr = [1,2,3];let [a,b,c] = arr;console.log('a='+a);console.log('b='+c);console.log('c='+c);}
相当于让变量a/b/c自动匹配数组的前三个元素。
2.2 对象解构
我们定义一个对象。
let person = {"name": "George","age": 21,"language":['js','java']
}
可以采用如下方式获取对象属性值。
let name = person.name;
let age = person.age;
let language = person.language;
ES6的解构语法允许如下方式获取对象属性。
let [name,age,language] = person;
3,字符串
ES6(ECMAScript 6 或 ES2015)为字符串处理带来了一些重要的改进。
3.1 插值字符串
插值字符串允许你在字符串中嵌入表达式,使用反引号 ``
包围字符串,并且可以用 ${expression}
的形式插入任何 JavaScript 表达式的值。
let name = "Alice";
let greeting = `Hello, ${name}!`;
console.log(greeting); // 输出: Hello, Alice!
在插值字符串中,可以有表达式,也可以有函数调用。
let name = "Alice";
let age = 10;
let greeting = `Hello, ${name}, i am ${age + 6} years old, i am ${work()}!`;
console.log(greeting); // 输出: Hello, Alice!function work() {console.log('programing...')
}
3.2 Unicode 支持增强
ES6 改进了对 Unicode 字符的支持,特别是对于那些超过基本多文种平面(BMP)的字符,也就是那些码点超过 U+FFFF 的字符。例如,你可以使用 \u{hhhh}
的形式来表示任何 Unicode 码点。
示例:
let emoji = '\u{1F600}';
console.log(emoji); // 输出: 😄
3.3 遍历器接口(Iterator Protocol)
ES6 引入了 for...of
循环,可以直接遍历字符串中的每个字符,这在处理长字符串或需要逐字符操作时非常方便。
示例:
for (let char of "hello") {console.log(char);
}
// 输出:
// h
// e
// l
// l
// o
3.4 新的字符串方法
ES6 引入了几种新的字符串方法,使得字符串的检查和操作更加直观:
includes()
:检查字符串是否包含另一个字符串。startsWith()
:检查字符串是否以指定的子串开始。endsWith()
:检查字符串是否以指定的子串结束。
示例:
let str = "Hello World!";
console.log(str.includes("World")); // 输出: true
console.log(str.startsWith("Hello")); // 输出: true
console.log(str.endsWith("!")); // 输出: true
3.5 normalize()
方法
此方法可以将字符串转换为标准的 Unicode 形式,这在处理包含重音符号和其他特殊字符的文本时特别有用。
示例:
let str = "café";
let normalizedStr = str.normalize("NFD");
console.log(normalizedStr); // 输出: c a ̧ f é
3.6 多行字符串
在ES6(ECMAScript 2015)中,多行字符串的创建变得更加简单和直观。在ES5及之前的版本中,如果你想创建一个多行字符串,你需要使用反斜杠\
作为续行符,或者使用加号+
将多行字符串拼接在一起。这种方法不仅繁琐,而且可能会导致代码的可读性降低。
ES6引入了模板字符串(Template Literals),这是一种使用反引号`
包围字符串的新方法。模板字符串不仅支持行内表达式的嵌入,还天然支持多行字符串的创建,无需额外的转义字符或拼接操作。
3.6.1 创建多行字符串
使用模板字符串创建多行字符串非常简单,你只需在反引号之间输入你的文本即可,包括换行符。这样,你的字符串将保留所有的换行和空白。
示例代码:
let multilineString = `
这是第一行文本。
这是第二行文本,
它包含了几个单词。
`;console.log(multilineString);
当你运行上述代码时,控制台输出将会显示一个带有正确换行的多行字符串。
3.6.2 保留或移除空白
默认情况下,模板字符串会保留字符串中的所有空白和换行符。但是,如果你希望移除字符串开始和结尾的空白以及每行前面的空白,你可以使用标签模板函数。ES6引入了一个内置的标签函数tag
,叫做String.raw
,它可以生成一个未经过处理的原始字符串,其中的空白和缩进会被移除。
示例代码:
let rawMultilineString = String.raw`
这是第一行文本。这是第二行文本,它包含了几个单词。
`;console.log(rawMultilineString);
在这个例子中,rawMultilineString
中的第二行前面的四个空格将被忽略,因为它使用了String.raw
标签。
ES6的模板字符串提供了一种优雅的方式来创建和操作多行字符串,使得代码更加简洁和易于阅读。这对于需要处理大量文本数据的场景,如HTML模板、配置文件或任何需要多行文本的代码片段,都是非常有用的。
4,函数新特性
ES6提供了一些函数新特性,提供了更加灵活和简洁的语法。
4.1 参数默认值
在 ES6 以前,我们无法给一个函数参数设置默认值,只能采用变通写法。
function add(a, b) {
// 判断 b 是否为空,为空就给默认值 1
b = b || 1;
return a + b;
}
// 传一个参数
console.log(add(10));
ES6允许在声明函数时,指定参数的默认值。
function add2(a , b = 1) {return a + b;
}
// 传一个参数
console.log(add2(10));
注意,有默认值的参数必须放在最后。
下面的函数声明了三个参数,给第二个参数设置默认值的写法是不符合默认值语法的,编译不通过。。
function add2(a , b = 1, c) {return a + b + c;
}
4.2 不定参数
不定参数用来表示不确定参数个数,形如,…变量名,由…加上一个具名参数标识符组成。
不定参数只能放在参数列表的最后,并且有且只有一个不定参数。
function fun(...values) {console.log(values.length)
}// 除了不定参数,函数还可以有其他参数
function fun1(param1, ...values) {console.log(values.length)
}fun(1, 2) //2
fun(1, 2, 3, 4) //4
注意,不定参数必须放在参数列表的最后,以下函数声明是错误的。
function fun1(param1, ...values, param2) {console.log(values.length)
}
4.3 箭头函数
4.3.1 声明箭头函数
ES6 中新增了一种定义函数的简写方式,称之为箭头函数
。
//以前声明一个方法
var print = function (obj) {console.log(obj);
}// 可以简写为:
var print2 = obj => console.log(obj);// 测试调用
print(100);
print2(100);
// 两个参数的情况:
var sum = function (a, b) {return a + b;
}//用箭头函数改写
// 当只有一行语句,并且需要返回结果时,可以省略 {} , 结果会自动返回。
var sum2 = (a, b) => a + b;//测试调用
console.log(sum2(10, 10));//20// 代码不止一行,可以用`{}`括起来
var sum3 = (a, b) => {c = a + b;return c;
};//测试调用
console.log(sum3(10, 20));//30
4.3.2 箭头函数结合解构表达式
//需求,声明一个对象,hello 方法需要对象的个别属性
// 传统函数声明
const person = {name: "jack",age: 21,language: ['java', 'js', 'css']
}function hello(person) {console.log("hello," + person.name)
}// 用箭头函数和对象结构重构
var hello2 = ({ name }) => { console.log("hello," + name) };//测试
hello2(person);
5,数组的Map和Reduce方法
理解ES6中数组的map()
和reduce()
方法是非常重要的,它们能更简洁地操作和转换数组数据。下面我将分别介绍这两个方法的用途、语法和一些基本的使用示例。
5.1 map() 方法
map()
方法用于创建一个新数组,其结果是调用数组中的每个元素上的一个函数。这个函数通常称为映射函数,因为它将一个数组映射到另一个数组。原数组不会被修改。
const newArray = array.map(callback(currentValue[, index[, array]])[, thisArg])
callback
是一个必需的函数,用于处理数组中的每个元素。currentValue
是当前正在处理的数组元素。index
可选,是当前元素在数组中的索引。array
可选,是调用map()
方法的原始数组。thisArg
可选,指定callback
函数执行时使用的this
值。
示例:
const numbers = [1, 2, 3, 4, 5];
const doubledNumbers = numbers.map(number => number * 2);
console.log(doubledNumbers); // 输出: [2, 4, 6, 8, 10]
注意,调用一个数组的map方法后,会生成一个新的数组,旧数组不变。
5.2 reduce() 方法
reduce()
方法用于将数组减少到一个单一的值。它通过一个叫做归约器函数的函数来完成,这个函数会累积结果。与map()
不同的是,reduce()
不返回一个新数组,而是返回一个单一的值。
语法:
const result = array.reduce(callback(preValue, currentValue[, index[, array]])[, initialValue])
callback
是一个必需的函数,用于处理数组中的每个元素。preValue
上一次调用函数callback
的结果,也是下一次调用的初始值。currentValue
是当前正在处理的数组元素。index
可选,是当前元素在数组中的索引。array
可选,是调用reduce()
方法的原始数组。initialValue
可选,作为第一次调用callback
函数的累积器的值。
示例:
const numbers = [1, 2, 3, 4, 5];
const sum = numbers.reduce((preValue, currentValue) => preValue+ currentValue, 0);
console.log(sum); // 输出: 15
下面逐步解析上述代码中 reduce()
函数的执行过程:
①. 初始化:
- 数组
numbers
被定义为[1, 2, 3, 4, 5]
。 reduce()
方法被调用,传递给它一个箭头函数(accumulator, currentValue) => accumulator + currentValue
和一个初始值0
。accumulator
在首次调用时将被设置为0
(初始值)。currentValue
将从数组的第一个元素开始,即1
。
②. 第一次迭代:
- 当前的
accumulator
是0
,currentValue
是1
。 - 回调函数
(0, 1) => 0 + 1
执行,结果是1
。 accumulator
更新为1
。
③. 第二次迭代:
- 现在
accumulator
是1
,currentValue
是数组的下一个元素2
。 - 回调函数
(1, 2) => 1 + 2
执行,结果是3
。 accumulator
更新为3
。
④. 第三次迭代:
accumulator
是3
,currentValue
是3
。- 回调函数
(3, 3) => 3 + 3
执行,结果是6
。 accumulator
更新为6
。
⑤. 第四次迭代:
accumulator
是6
,currentValue
是4
。- 回调函数
(6, 4) => 6 + 4
执行,结果是10
。 accumulator
更新为10
。
⑥. 第五次迭代:
accumulator
是10
,currentValue
是最后一个元素5
。- 回调函数
(10, 5) => 10 + 5
执行,结果是15
。 accumulator
更新为15
。
⑦. 结束迭代:
- 迭代完成,
reduce()
返回最终的accumulator
值,即15
。
⑧. 输出结果:
sum
变量现在等于15
。console.log(sum)
打印出15
。
这就是 reduce()
函数如何将一个数组 [1, 2, 3, 4, 5]
中的所有元素累加起来得到总和的过程。通过这种方式,reduce()
提供了一种非常灵活的方法来处理数组数据,可以用于求和、求乘积、查找最大值或最小值等多种场景。
6,Promise
在ES6中,Promise是一个用于异步编程的重要构造,它代表了一个最终可能完成或失败的异步操作,并且具有一个最终的值。
简单的说,Promise提供了一种新的异步调用的语法,让异步调用的语法更加简洁和容易理解。
接下里,我们将以一个例子深入浅出的说清楚Promise的来龙去脉。
6.1 场景说明
假设有这样一个需求,学生登录学校的考试系统,查询某一个的成绩。
实现这个简单的需求,要发出三次请求。
- 第一次请求,根据用户名查询用户ID,查询成功说明可以登录
- 第一次请求成功后,发出第二次请求,查询该用户有成绩的科目ID
- 第二次请求成功后,发出第三次请求,根据科目ID查询成绩
假设后台的数据存储在json文件中,整个请求过程如下。
第一次请求从后台的user.json
文件中查询到用户的ID为1。
// user.json:
{"id": 1,"name": "zhangsan","password": "123456"
}
第二次请求从后台的user_corse_1.json
中查询到用户有成绩的课程ID为10。
// user_corse_1.json:
{"id": 10,"name": "chinese"
}
第三次请求从后台的corse_score_10.json
中查询到用户课程ID成绩为90。
corse_score_10.json:
{"id": 100,"score": 90
}
6.2 回调地狱-传统实现
假设我们用JQuery的ajax实现异步请求,代码如下。
$.ajax({// 第一次请求url: "mock/user.json",success(data) {console.log("查询用户:", data);$.ajax({// 第二次请求url: `mock/user_corse_${data.id}.json`,success(data) {console.log("查询到课程:", data);$.ajax({// 第三次请求url: `mock/corse_score_${data.id}.json`,success(data) {console.log("查询到分数:", data);},error(error) {console.log("出现异常了:" + error);}});},error(error) {console.log("出现异常了:" + error);}});},error(error) {console.log("出现异常了:" + error);}
});
上面代码仅仅有三次回调,如果回答次数更多,嵌套的更深,导致代码难以阅读和理解,这就是所谓的回调地狱
。
6.3 使用Promise重构
6.3.1 Promise 语法
const promise = new Promise(function (resolve, reject) {// 执行异步操作if (/* 异步操作成功 */) {resolve(value);// 调用 resolve,代表 Promise 将返回成功的结果} else {reject(error);// 调用 reject,代表 Promise 会返回失败结果}
});
使用箭头函数简化。
const promise = new Promise((resolve, reject) =>{// 执行异步操作if (/* 异步操作成功 */) {resolve(value);// 调用 resolve,代表 Promise 将返回成功的结果} else {reject(error);// 调用 reject,代表 Promise 会返回失败结果}
});
如果要等待异步执行完成之后,再执行下一个特定任务,可以通过 promise 的 then 方法来实现,还可以跟上 catch处理 promise 异步执行失败的事件。
promise.then(function (value) {// 异步执行成功后的回调
}).catch(function (error) {// 异步执行失败后的回调
})
6.3.2 用Promise实现上述需求
new Promise((resolve, reject)=>{$.ajax({url: "mock/user.json",success(data) {console.log("Promise查询用户:", data);resolve(data.id);},error(error) {console.log("Promise出现异常了:" + error);reject(error);}});}).then(id=>{return new Promise((resolve, reject)=>{$.ajax({url: `mock/user_corse_${id}.json`,success(data) {console.log("Promise查询到课程:", data);resolve(data.id);},error(error) {console.log("Promise出现异常了:" + error);reject(error);}});});}).then(id=>{return new Promise((resolve, reject)=>{$.ajax({url: `mock/corse_score_${id}.json`,success(data) {console.log("Promise查询到分数:", data);resolve(data);},error(error) {console.log("Promise出现异常了:" + error);reject(error);}});});}).then(({score})=>{console.log("Promise查询到分数:", score);})
下面重构上述代码,使之更为简洁。
把发送请求的代码抽象为一个公共的方法,减少冗余代码,代码结构更为清晰易懂。
let sendRequest = function (url, params) { return new Promise((resolve, reject) => {$.ajax({url: url,type: "GET",data: params,success(result) {resolve(result);},error(error) {reject(error);}});})
}
于是代码可以重构为:
var sendRequest = function (url, params) {return new Promise((resolve, reject) => {$.ajax({url: url,type: "GET",data: params,success(result) {console.log(result);resolve(result.id);},error(error) {reject(error);}});})}sendRequest("mock/user.json").then(id => {console.log("Promise111查询到id:", id);return sendRequest(`mock/user_corse_${id}.json`);}).then(id => {console.log("Promise1113301查询到id: " + id);return sendRequest(`mock/corse_score_${id}.json`);}).then(({ score }) => {console.log("Promise222查询到分数:", score);})
经过重构后的代码明显变得简洁易读的多,但前提是需要对Promise有一定的熟悉度,否则也是很难理解的,多写多思考。
相关文章:

谷粒商城实战笔记-29~34-前端基础 - ES6
文章目录 零,安装Live Server插件一,创建前端工程1,创建工程2,在工程ES6中创建一个html文件 二,ES6 简介1,ES6 的历史 三,前端基础ES61,let 和 const1.1,let1.1.1 严格的…...
浔川官方撤销浔川总社部社长王*职位——浔川官方
2024年7月13日晚9点半,浔川社团举报中心接到举报, 询问情况后,才知,浔川社团前日(7月13日)发布了一篇文章《浔川回应浔川官方宣布官方账号将在CSDN进行无人管理——浔川官方》文章会被删除,官方…...

小白学python(第七天)
哈哈,这个系列的文章也有一段时间没更新,主要是最近在忙c嘎嘎,不过没事接下来会优先更python啦,那么我们先进入正题吧 函数的定义及调用 函数定义 格式:def 函数名(形参列表): 语…...
npm和yarn清理缓存命令
yarn清除缓存 1、查看yarn全局缓存目录 yarn cache dir2、清除缓存 yarn cache cleannpm 清除缓存 1、将node-modules文件夹先删除 2、清理缓存命令: npm cache clean --force3、重新安装一次即可 npm install /cnpm install...

数据结构之初始二叉树(1)
找往期文章包括但不限于本期文章中不懂的知识点: 个人主页:我要学编程(ಥ_ಥ)-CSDN博客 所属专栏:数据结构(Java版) 目录 树型结构 树的概念 与树的有关概念 树的表示形式 树的应用 二叉树 概念 两种特殊的…...

STM32-寄存器点灯案例详解
本文以PA1引脚点亮LED灯为案例,解析了STM32寄存器操作的配置过程,以及从手册查询方法和寄存器配置步骤。 一、概念 1.十六进制和二进制之间相互转换关系 首先,需要了解十六进制和二进制之间的基本转换方法。十六进制是一种基数为16的数制&…...

Github Action 自动部署更新静态网页服务
本文首发于 Anyeの小站,点击跳转 获得更优质的阅读体验 前言 贴一段胡话 在用过 应用:静态网页服务 之后,事实证明: 总而言之,自动化是一个很令人着迷的东西,摆脱重复繁琐的工作,解放了双手的…...
如何在CSS中控制动画的触发位置?
如何在CSS中控制动画的触发位置? 在CSS中控制动画的触发位置主要是通过transform属性来实现的。例如,如果你希望动画从某个固定的位置开始,可以设置transform: translate(x, y),其中x和y是你想让元素偏离其原始位置的距离。对于动…...

MFC流的形式读取图片
1.基于对话框布置控件 2.给控件绑定变量 3.给按钮控件添加响应函数 void CMFC流的形式读取图片Dlg::OnBnClickedButton1() {// TODO: 在此添加控件通知处理程序代码//HDC mECGDC; // 设备描述表句柄//CPen mECGDrawPen; // ECG波形画笔//RECT mECGRect; // 在该矩形区域内画…...

查找PPT中某种字体的全部对应文字
本文章的目的是找到某种字体的文字,而不是替换某种字体的文字,也不是将某种字体全部替换为另外一种文字。 第一步:在PPT中按下ALTF11 出现以下窗口 第二步:点击插入->模块 第三步:将以下代码输入到窗体中 Sub F…...
相机光学(三十一)——暗房设置的要求
ISO标准通常在测试相机时指定对周围条件的要求。由于摄影ISO组试图保持这些要求与所有标准一致,所以我们总结了这个“技术说明”中的重要方面。 温度应保持在23C /- 2C的范围内。在设计空调系统时,请记住图表照明的耗电量和发热量。湿度需要在&#…...

Linux安全技术与防火墙
一、安全技术和防火墙 1.1 安全技术 入侵检测系统:特点是不阻断网络访问,主要是提供报警和时候报警,不主动介入。 入侵防御系统:透明模式工作,对数据包、网络监控、服务攻击、木马蠕虫、系统漏洞等等进行准确的分析和…...

C#中简单Socket编程
C#中简单Socket编程 Socket分为面向连接的套接字(TCP套接字)和面向消息的套接字(UDP 套接字)。我们平时的网络编程是对Socket进行操作。 接下来,我用C#语言来进行简单的TCP通信和UDP通信。 一、TCP通信 新建项目SocketTest,首先添加TCP通信的客户端代…...

UNIAPP_ReferenceError: TextEncoder is not defined 解决
错误信息 1、安装text-decoding npm install text-decoding2、main.js import { TextEncoder, TextDecoder } from text-decoding global.TextEncoder TextEncoder global.TextDecoder TextDecoder...

科普文:微服务技术栈梳理
概叙 如上两图所示,微服务架构下,需要的组件很多,上面中也并未列全。下面将梳理一下国内微服务架构下,用到的技术栈,仅供参考。 科普文:12种常见的软件架构-CSDN博客 没有最好的架构,只有最适…...

如何使用HTML和JavaScript读取文件夹中的所有图片并显示RGB范围
如何使用HTML和JavaScript读取文件夹中的所有图片并显示RGB范围 在这篇博客中,我将介绍如何使用HTML和JavaScript读取文件夹中的所有图片,并显示这些图片以及它们的RGB范围。这个项目使用现代浏览器提供的<input type"file" webkitdirecto…...

PDF公式转Latex
文章目录 摘要数据集 UniMER介绍下载链接 LaTeX-OCRUniMERNet安装UniMER 用的数据集介绍下载链接 PDF-Extract-Kit整体介绍效果展示评测指标布局检测公式检测公式识别 使用教程环境安装参考[模型下载](models/README.md)下载所需模型权重 在Windows上运行在macOS上运行运行提取…...

excel 百分位函数 学习
提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 前言一、函数说明PERCENTILE 函数PERCENTILE.inc 函数PERCENTILE.exc 函数QUARTILE.EXC 函数 二、使用步骤总结 前言 excel 百分位函数 Excel提供了几个函数用于…...

(十一) Docker compose 部署 Mysql 和 其它容器
文章目录 1、前言1.1、部署 MySQL 容器的 3 种类型1.2、M2芯片类型问题 2、具体实现2.1、单独部署 mysql 供宿主机访问2.1.1、文件夹结构2.1.2、docker-compose.yml 内容2.1.3、运行 2.2、单独部署 mysql 容器供其它容器访问(以 apollo 为例)2.2.1、文件…...

提高项目透明度:有效的跟踪软件
国内外主流的10款项目进度跟踪软件对比:PingCode、Worktile、Teambition、Tower、Asana、Trello、Jira、ClickUp、Notion、Liquid Planner。 在项目管理中,确保进度跟踪的准确性与效率是每位项目经理面临的主要挑战之一。选用合适的项目进度跟踪软件不仅…...

8k长序列建模,蛋白质语言模型Prot42仅利用目标蛋白序列即可生成高亲和力结合剂
蛋白质结合剂(如抗体、抑制肽)在疾病诊断、成像分析及靶向药物递送等关键场景中发挥着不可替代的作用。传统上,高特异性蛋白质结合剂的开发高度依赖噬菌体展示、定向进化等实验技术,但这类方法普遍面临资源消耗巨大、研发周期冗长…...

iPhone密码忘记了办?iPhoneUnlocker,iPhone解锁工具Aiseesoft iPhone Unlocker 高级注册版分享
平时用 iPhone 的时候,难免会碰到解锁的麻烦事。比如密码忘了、人脸识别 / 指纹识别突然不灵,或者买了二手 iPhone 却被原来的 iCloud 账号锁住,这时候就需要靠谱的解锁工具来帮忙了。Aiseesoft iPhone Unlocker 就是专门解决这些问题的软件&…...
React Native在HarmonyOS 5.0阅读类应用开发中的实践
一、技术选型背景 随着HarmonyOS 5.0对Web兼容层的增强,React Native作为跨平台框架可通过重新编译ArkTS组件实现85%以上的代码复用率。阅读类应用具有UI复杂度低、数据流清晰的特点。 二、核心实现方案 1. 环境配置 (1)使用React Native…...
sqlserver 根据指定字符 解析拼接字符串
DECLARE LotNo NVARCHAR(50)A,B,C DECLARE xml XML ( SELECT <x> REPLACE(LotNo, ,, </x><x>) </x> ) DECLARE ErrorCode NVARCHAR(50) -- 提取 XML 中的值 SELECT value x.value(., VARCHAR(MAX))…...
3403. 从盒子中找出字典序最大的字符串 I
3403. 从盒子中找出字典序最大的字符串 I 题目链接:3403. 从盒子中找出字典序最大的字符串 I 代码如下: class Solution { public:string answerString(string word, int numFriends) {if (numFriends 1) {return word;}string res;for (int i 0;i &…...

Android 之 kotlin 语言学习笔记三(Kotlin-Java 互操作)
参考官方文档:https://developer.android.google.cn/kotlin/interop?hlzh-cn 一、Java(供 Kotlin 使用) 1、不得使用硬关键字 不要使用 Kotlin 的任何硬关键字作为方法的名称 或字段。允许使用 Kotlin 的软关键字、修饰符关键字和特殊标识…...

学习STC51单片机32(芯片为STC89C52RCRC)OLED显示屏2
每日一言 今天的每一份坚持,都是在为未来积攒底气。 案例:OLED显示一个A 这边观察到一个点,怎么雪花了就是都是乱七八糟的占满了屏幕。。 解释 : 如果代码里信号切换太快(比如 SDA 刚变,SCL 立刻变&#…...
服务器--宝塔命令
一、宝塔面板安装命令 ⚠️ 必须使用 root 用户 或 sudo 权限执行! sudo su - 1. CentOS 系统: yum install -y wget && wget -O install.sh http://download.bt.cn/install/install_6.0.sh && sh install.sh2. Ubuntu / Debian 系统…...
Go语言多线程问题
打印零与奇偶数(leetcode 1116) 方法1:使用互斥锁和条件变量 package mainimport ("fmt""sync" )type ZeroEvenOdd struct {n intzeroMutex sync.MutexevenMutex sync.MutexoddMutex sync.Mutexcurrent int…...

GO协程(Goroutine)问题总结
在使用Go语言来编写代码时,遇到的一些问题总结一下 [参考文档]:https://www.topgoer.com/%E5%B9%B6%E5%8F%91%E7%BC%96%E7%A8%8B/goroutine.html 1. main()函数默认的Goroutine 场景再现: 今天在看到这个教程的时候,在自己的电…...