Vue3学习记录(三)--- 组合式API之生命周期和模板引用
一、生命周期
1、简介
生命周期,指的是一个 Vue 实例从创建到销毁的完整阶段,强调的是一个时间段。
生命周期钩子函数,指的是 Vue 实例提供的内置函数,函数的参数为一个回调函数。这些钩子函数会在实例生命周期的某些固定时间点,依次按序执行其内部的回调函数。我们只需要在回调函数内部书写要执行的代码即可。
在调用生命周期钩子函数时,Vue会自动将其回调函数注册到当前正在初始化 Vue 组件实例上,因此这些钩子函数应当在组件初始化时被同步注册,不可以在异步操作中调用这些钩子函数。因为当异步操作开始执行时,当前组件实例已经初始化完成,调用的钩子函数无法被注册到组件实例上。
当然生命周期钩子函数也可以在一个外部函数中调用,只要调用栈是同步的,且最终起源自 <script setup>
就可以。
生周期图示:
2、生命周期钩子函数
首先,在Vue3的组合式API中并不存在created()
和beforeCreate()
这两个生命周期钩子函数,而是通过setup
实现了更灵活的生命周期钩子函数,直接书写在<script setup>
模块中的全局代码,相当于这两个钩子函数中的代码。
① onBeforeMount()
function onBeforeMount(callback: () => void): void
该钩子函数会在组件实例被挂载到页面上之前被调用,此时组件中的响应式数据和函数方法等已经设置完成,可以在此阶段进行数据初始化计算操作。但此时组件中的DOM节点还没有被创建,此时无法操作DOM。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
案例代码:
<template><div><h1>{{ text }}</h1></div>
</template><script setup>
// 引入要使用的模块
import { ref, onBeforeMount } from 'vue'// 声明一个响应式变量
let text = ref('这是一个大标题')
// 声明一个函数
const changeTest = (value) => {text.value = value
}
// 使用onBeforeMount()钩子函数
onBeforeMount(() => {// 调用响应变量console.log(text.value); // 这是一个大标题// 调用函数changeTest('这是修改后的大标题')console.log(text.value); // 这是修改后的大标题// 尝试操作dom console.log(document.querySelector('h1')); // null 此时DOM还未渲染到页面上 无法被获取
})
</script>
② onMounted()
function onMounted(callback: () => void): void
该生命周期钩子函数会在组件实例被挂载到页面上之后被调用,此时组件中的DOM结构和其同步子组件中的DOM结构都已经被挂载到页面上了,我们可以在此阶段进行 DOM 操作。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
案例代码:
// 承接上个案例的代码... // 引入要使用的模块
import { ref, onBeforeMount, onMounted } from 'vue'// 使用onMounted()钩子函数
onMounted(() => {// 调用响应变量console.log(text.value); // 这是修改后的大标题// 调用函数changeTest('这是再次修改后的大标题')console.log(text.value); // 这是再次修改后的大标题// 尝试操作dom console.log(document.querySelector('h1')); // 成功获取DOM <h1>这是再次修改后的大标题</h1>
})// 其他...
③ onBeforeUpdate()
function onBeforeUpdate(callback: () => void): void
该钩子函数会在组件由于响应式状态变更,而引起的 DOM 树更新之前调用,此时获取DOM节点中的相关状态,还是未更新之前的状态;获取响应式状态,获取的是更新后的状态。我们可以在此阶段根据更新前后的数据状态进行相应操作。
在onMounted()
钩子函数中进行会引起DOM更新的响应式状态变更,也会触发当前钩子函数;在onBeforeMount()
中的状态变更则不会,因为此时DOM结构还没有渲染到页面上。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
案例代码:
<template><div><h1>{{ text }}</h1><button @click="changeTest('点击修改标题')">改变标题</button></div>
</template><script setup>
// 引入要使用的模块
import { ref, onBeforeUpdate } from 'vue'// 声明一个响应式变量
let text = ref('这是一个大标题');// 声明一个函数
const changeTest = (value) => {text.value = value
}// 使用onBeforeUpdate()钩子函数
onBeforeUpdate(() => {// 输出变更后的响应式变量值console.log(text.value); // 点击修改标题// 获取 DOM 输出未更新的DOM状态值console.log(document.querySelector('h1').innerText) // 这是一个大标题
})
</script>
④ onUpdated()
function onUpdated(callback: () => void): void
该钩子函数会在组件由于响应式状态变更,而引起的 DOM 树更新之后调用。此时获取DOM节点中的相关状态,获取的将是更新后的状态。这个钩子会在组件的 DOM 更新后被调用,这些更新可能是由不同的响应式状态变更引起的。
不要在该阶段更改组件中的响应式状态,这肯有可能会导致无限死循环。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
案例代码:
<template><div><h1>{{ text }}</h1><button @click="changeTest('点击修改标题')">改变标题</button></div>
</template><script setup>
// 引入要使用的模块
import { ref, onUpdated } from 'vue'// 声明一个响应式变量
let text = ref('这是一个大标题');// 声明一个函数
const changeTest = (value) => {text.value = value
}// 使用onUpdated()钩子函数
onUpdated(() => {// 输出变更后的响应式变量值console.log(text.value); // 点击修改标题// 获取 DOM 输出更新后的DOM状态值console.log(document.querySelector('h1').innerText) // 点击修改标题
})
</script>
⑤ onBeforeUnmount()
function onBeforeUnmount(callback: () => void): void
该钩子函数在组件实例被销毁之前调用,此时组件中的所有功能保持可用,可以在这一阶段做一些清理工作,例如取消订阅、清除定时器、释放资源等。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
案例代码:
// 引入要使用的模块
import { onBeforeUnmount } from 'vue'// 使用onBeforeUnmount()钩子函数
onBeforeUnmount(() => {// 做一些清理工作,释放占用的资源
})
⑥ onUnmounted()
function onUnmounted(callback: () => void): void
该钩子函数在组件实例被销毁之后调用,此时当前组件的所有子组件都已经被卸载,且所有响应式状态(变量、计算属性、侦听器等)都停止作用了。这一阶段也可以做一些清理工作,例如取消订阅、清除定时器、释放资源等。但是尽量不要在该阶段进行一些耗时的操作,以免影响组件销毁的性能。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
案例代码:
// 引入要使用的模块
import { onUnmounted } from 'vue'// 使用onUnmounted()钩子函数
onUnmounted(() => {// 做一些清理工作,释放占用的资源
})
⑦ onActivated()
function onActivated(callback: () => void): void
该钩子函数需要与<KeepAlive>
结合使用,如果组件是<KeepAlive>
中缓存组件的一部分,当组件被插入到DOM中时(包括首次挂载和从缓存重新挂载),会触发该钩子函数。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
⑧ onDeactivated()
function onDeactivated(callback: () => void): void
该钩子函数需要与<KeepAlive>
结合使用,如果组件是<KeepAlive>
中缓存组件的一部分,当组件从DOM中被移除时(包括进入缓存和组件卸载),会触发该钩子函数。
该钩子函数在服务端渲染期间不会被调用,只会在客户端执行。
⑨ onErrorCaptured()
function onErrorCaptured(callback: ErrorCapturedHook): voidtype ErrorCapturedHook = (err: unknown,instance: ComponentPublicInstance | null,info: string
) => boolean | void
该钩子函数会在捕获当前组件内的后代组件传递的错误时调用,错误源包括:组件渲染错误、事件处理器错误、侦听器错误等等。三个实参分别表示:错误对象、触发该错误的组件实例,以及一个说明错误来源类型的信息字符串。
如果组件的继承链或组件链上存在多个 errorCaptured
钩子函数,对于同一个错误,这些钩子会被按从底至上的顺序,一一向上传递并调用errorCaptured
钩子函数。
默认情况下,所有的错误都会被一层层向上传递,最终到达全局应用级的 app.config.errorHandler
(前提是这个函数已经定义),如果我们在当前钩子函数中return false;
,则会阻止错误向上传递,app.config.errorHandler
也无法监听到。
⑩ onRenderTracked()
function onRenderTracked(callback: DebuggerHook): voidtype DebuggerHook = (e: DebuggerEvent) => voidtype DebuggerEvent = {effect: ReactiveEffecttarget: objecttype: TrackOpTypes /* 'get' | 'has' | 'iterate' */key: any
}
该钩子函数会在当前组件的组件模板渲染过程中追踪到响应式依赖时调用。且仅在开发模式下可用,在服务器端渲染期间不会被调用。
⑪ onRenderTriggered()
function onRenderTriggered(callback: DebuggerHook): voidtype DebuggerHook = (e: DebuggerEvent) => voidtype DebuggerEvent = {effect: ReactiveEffecttarget: objecttype: TriggerOpTypes /* 'set' | 'add' | 'delete' | 'clear' */key: anynewValue?: anyoldValue?: anyoldTarget?: Map<any, any> | Set<any>
}
该钩子函数会在当前组件内响应式依赖发生变更并触发了组件渲染时调用。且仅在开发模式下可用,在服务器端渲染期间不会被调用。
⑫ onServerPrefetch()
function onServerPrefetch(callback: () => Promise<any>): void
该钩子函数,只会在当前组件示例在服务器上被渲染之前调用。
3、父子组件的生命周期钩子函数执行顺序
组件挂载阶段:
在父组件和子组件同事挂载到页面上时,会按照以下顺序执行挂载阶段的钩子函数:
- 父组件的
<script setup>
(相当于created()
和beforeCreate()
)。 - 父组件的
onBeforeMount()
钩子函数。 - 子组件的
<script setup>
(相当于created()
和beforeCreate()
)。 - 子组件的
onBeforeMount()
钩子函数。 - 子组件的
onMounted()
钩子函数。 - 父组件的
onMounted()
钩子函数。
组件更新阶段:
只有当父子组件同时发生更新时,两者的更新阶段钩子函数才会都被触发。如果单独只在父组件内发生更新或只在子组件内发生更新,则只会触发相应组件内的更新钩子函数。
- 父组件的
onBeforeUpdate()
钩子函数。 - 子组件的
onBeforeUpdate()
钩子函数。 - 父组件的
onUpdated()
钩子函数。 - 子组件的
onUpdated()
钩子函数。
组件销毁阶段:
当父组件被销毁时,其内部的子组件也会一并被销毁,并按照以下顺序执行销毁阶段的钩子函数。
- 父组件的
onBeforeUnmount()
钩子函数。 - 子组件的
onBeforeUnmount()
钩子函数。 - 子组件的
onUnmounted()
钩子函数。 - 父组件的
onUnmounted()
钩子函数。
二、模板引用
1、简介
模板引用是Vue提供给我们用来操作DOM的一种方法,通过为DOM元素设置一个ref
attribute属性,并设置属性值为一个响应式变量,从而获取对该DOM元素的引用。然后就可以对获取的DOM进行操作,例如:获取焦点、改变样式等等。
模板引用可以获取对普通DOM元素的引用,也可以获取对组件实例的引用。但只有当目标DOM渲染到页面上后,才可以通过响应式变量来获取该DOM的引用,并对其进行操作。
2、普通DOM的引用
想要获取一个普通DOM的引用,首先需要声明一个响应式变量,然后将该变量的名字设置为目标DOM的ref
属性的属性值即可,最终就可以通过响应式变量来访问对应的DOM。
案例代码:
<template><div><!-- 给DOM元素增加一个ref属性 属性值与响应式变量名相同 --><h1 ref="h1DOM">这是一个普通DOM</h1></div>
</template><script setup>
import { ref, onBeforeMount, onMounted, watchEffect } from 'vue';
// 声明一个响应式变量 变量名与模板中的ref属性值相同
const h1DOM = ref(null);watchEffect(() => {console.log('监听h1DOM属性值的变化----',h1DOM.value); // 初始为null 之后为对应DOM对象
})onBeforeMount(() => {// onBeforeMount阶段DOM还未挂载,所以获取不到DOMconsole.log('beforeMount中获取模板引用----',h1DOM.value); // null
})onMounted(() => {// onMounted阶段DOM已经挂载,可以获取到DOMconsole.log('onMounted中获取模板引用----',h1DOM.value); // 相应DOM
})
</script>
3、v-for列表渲染DOM的引用
v3.2.25 版本新增,可以通过模板引用,获取使用v-for
进行列表渲染的DOM元素,获取结果为一个数组,包含列表渲染出来的所有元素,但是并不保证获取的元素数组的顺序与页面上元素的顺序相同。
同样,首先需要声明一个响应式变量,然后将该变量的名字设置为目标DOM的ref
属性的属性值即可。
案例代码:
<template><div><!-- 给DOM元素增加一个ref属性 属性值与响应式变量名相同 --><div v-for="item in 5" ref="domList">{{ item }}</div></div>
</template><script setup>
import { ref, onMounted } from 'vue';
// 声明一个响应式变量 变量名与模板中的ref属性值相同
const domList = ref(null);onMounted(() => {// onMounted阶段DOM已经挂载,可以获取到DOMconsole.log('onMounted中获取模板引用----',domList.value); // 列表渲染的所有DOM// 遍历domList中的所有DOMdomList.value.forEach((item) => {console.log(item); // DOM})
})
</script>
4、模板引用函数
除了给DOM的ref
属性赋值一个响应式变量之外,还可以通过:
动态给ref
属性绑定一个函数,每次组件更新时,都会触发绑定的函数,绑定函数的第一个参数就是当前DOM的引用。
当绑定元素被卸载时,ref绑定的函数也会被调用一次,不过此时表示DOM引用第一个参数值为null
。
案例代码:
<template><div><!-- 绑定函数 --><input :ref="(el) => console.log('这是绑定了匿名函数的ref',el)" /><input :ref="test" /></div>
</template><script setup>const test = (el) => {console.log('这是绑定js方法的ref----',el);
}
</script>
5、组件实例的引用
当一个子组件加入的父组件中时,可以通过模板引用的方式,给其设置ref
属性,从而获取到这个子组件的组件实例。
如果这个子组件使用的是选项式API或者使用setup()
钩子函数的组合式API,则获取的组件实例与子组件的this
完全相同,我们可以通过该组件实例访问子组件的每一个属性和方法,从而实现一些父子组件中的交互。当然这种方式并不推荐使用,因为可能会引起逻辑混乱,大多数情况下,还是推荐使用使用标准的 props 和 emit 接口来实现父子组件交互。
但如果子组件使用的是<script setup>
形式的组合式API,则该组件的属性和方法默认是私有的,默认情况下,获取的组件实例是无法访问组件中的任何属性和方法的。除非子组件通过defineExpose()
宏方法(宏方法无需导入,可直接使用)主动向外暴露出一部分属性和方法,然后获取的组件实例才可以访问这些被主动暴露的属性和方法。
案例代码:
使用<script setup>
形式的子组件Child.vue:
<template><div> <h3>这是一个子组件</h3></div>
</template><script setup>
import { ref } from 'vue'
// 声明一个响应式变量
const son = ref('我是script setup中的一个变量')
const son2 = ref('我是script setup中的一个暴露出来的变量')// defineExpose 这样的编译器宏不需要导入
// 返回值会暴露给模板 能够被访问到
defineExpose({son2
})
</script>
使用setup()
钩子函数形式的子组件Child2.vue:
<template><div><h3>这是一个子组件</h3></div>
</template><script>
// 引入响应式API
import { ref } from 'vue'export default {// 使用setup()钩子函数setup() {// 声明响应式变量const son = ref('我是setup()钩子函数中的一个变量')// 返回值会暴露给模板和其他的选项式 API return {son}},
};
</script>
使用选项式API的子组件Child3.vue:
<template><div><h3>这是一个子组件</h3></div>
</template><script>
export default {name: 'ViteProjectChild',data() {return {son: '我是选项式API中的一个变量'};},
};
</script>
父组件:
<template><div><!-- 引入子组件 --><Child ref="son1"></Child><Child2 ref="son2"></Child2><Child3 ref="son3"></Child3></div>
</template><script setup>
import { ref, onMounted } from 'vue';
import Child from '../components/Child.vue';
import Child2 from '../components/Child2.vue';
import Child3 from '../components/Child3.vue';const son1 = ref(null);
const son2 = ref(null);
const son3 = ref(null);onMounted(() => {console.log('获取script setup的组合式API子组件----',son1.value); console.log('获取script setup的组合式API子组件的属性----',son1.value.son);console.log('获取script setup的组合式API子组件的属性2----',son1.value.son2);console.log('获取setup()钩子函数的组合式API子组件----',son2.value); console.log('获取setup()钩子函数的组合式API子组件的属性----',son2.value.son); console.log('获取选项式API的子组件----',son3.value); console.log('获取选项式API的子组件的属性----',son3.value.son);
})
</script>
页面效果:
相关文章:

Vue3学习记录(三)--- 组合式API之生命周期和模板引用
一、生命周期 1、简介 生命周期,指的是一个 Vue 实例从创建到销毁的完整阶段,强调的是一个时间段。 生命周期钩子函数,指的是 Vue 实例提供的内置函数,函数的参数为一个回调函数。这些钩子函数会在实例生命周期的某些固定…...

Batch Normalization和Layer Normalization和Group normalization
文章目录 前言一、Group normalization二、批量规范化(Batch Normalization)三、层规范化(Layer Normalization) 前言 批量规范化和层规范化在神经网络中的每个批次或每个层上进行规范化,而GroupNorm将特征分成多个组,并在每个组内…...

命名实体识别NER(综合代码示例)
一、命名实体识别发展方向 二、中文数据集 CCKS2017开放的中文的电子病例测评相关的数据。 评测任务一:https://biendata.com/competition/CCKS2017_1/ 评测任务二:https://biendata.com/competition/CCKS2017_2/ CCKS2018开放的音乐领域的实体识别任务…...
关于jQuery日历插件:daterangepicker
关于options singleDatePicker: false 双日历,true 单日历 timePicker:false 不显示时分秒,true 显示时分秒 timePickerIncreament:1 默认值 {singleDatePicker : false, //是否显示单日历框 dateLimit : { days : 30 }, //起…...
【贪心算法】最大子序和
给你一个整数数组 nums ,请你找出一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。 子数组是数组中的一个连续部分。 示例 1: 输入:nums [-2,1,-3,4,-1,2,1,-5,4] 输出:6…...

爬虫逆向网站案例
一、相关网页 东方财富人气排行榜 二、查找url 三、寻找curl并复制 四、打开Convert curl commands to code (curlconverter.com) 五、修改并执行代码 import requestscookies {st_si: 73974981954644,st_pvi: 39724919122964,st_sp: 2024-03-05%2018%3A27%3A22,st_inirUrl:…...
蓝桥杯复习之前缀和
题目链接:https://www.luogu.com.cn/problem/P8649 思路: 看到区间和,第一反应肯定是前缀和,我们求出前缀和后对前缀和数组每一个值模k,然后对一个数组的值查看前面有几个相同的,举个例子:…...

动态规划(算法竞赛、蓝桥杯)--背包DP求具体方案
1、B站视频链接:E20 背包DP 求具体方案_哔哩哔哩_bilibili #include <bits/stdc.h> using namespace std; const int N1010; int v[N],w[N]; int f[N][N],p[N][N];int main(){int n,m;cin>>n>>m;for(int i1;i<n;i)cin>>v[i]>>w[i…...
go写mysql取得自增字段值
场景:有多张表,依据其中一张表的自增字段取得 id 值作为对象ID,然后使用这个Id插入到其他它表中。 如下一张 MySQL 的 innodb 表 X,用 go 编写程序,不指定 a 的值,指定 b 和 c 的值,往表 X 插入…...

Vue 3的Composition API和vue2的不同之处
Vue 3的Composition API是Vue.js框架的一个重要更新,它提供了一种新的组件逻辑组织和复用方式。在Vue 2中,我们通常使用Options API(data、methods、computed等)来组织组件的逻辑,但这种组织方式在处理复杂组件时可能会…...
go语言基础 -- 面向对象编程
go语言面向对象编程思想 面向对象编程离不开封装、继承、多态三个特性,go语言与其他c、java不太一样,没有类的概念,面向对象的实现也有些区别,下面分别描述。 go语言封装 结构体中字段如欲对外隐藏,首字母小写&…...

HarmonyOS—编译构建概述
编译构建是将应用/服务的源代码、资源、第三方库等,通过编译工具转换为可直接在硬件设备上运行的二进制机器码,然后再将二进制机器码封装为HAP/APP软件包,并为HAP/APP包进行签名的过程。其中,HAP是可以直接运行在模拟器或真机设备…...
下载element-ui 资源,图标 element-icons.woff,element-icons.ttf 无法解码文件字体
css下载地址:https://unpkg.com/element-ui2.15.14/lib/theme-chalk/index.css js下载地址:https://unpkg.com/element-ui2.15.14/lib/index.js 图标及文字文件下载地址: element-icons.woff:: https://unpkg.com/element-…...

Flutter整体框架
Flutter整体框架由三部分组成:Framework、Engine和Embedder。 Framework Framework提供了一个用 Dart 语言编写的现代、反应式框架,由许多抽象的层级组成。它包括一套丰富的布局、动画、绘制、手势UI组件及配套代码,以及更基础的异步、文件、…...
JVM堆内存中新生代晋升到老年代的条件
1. 一般年龄判断 当对象在Eden区中经过第一次 Minor GC 后,如果仍然存活,则会被移动到 From Survivor 区,并且对象的年龄设为 1。每经过一次 Minor GC,存活下来的对象年龄加 1,若存活对象在 From Survivor 区的年龄达…...

前端监控为什么采用GIF图片做埋点?
一、什么是埋点监控 前端监控是开发人员用来跟踪和维护应用程序表现层的运行状况的过程和工具。它主要包括三种类型:数据监控、性能监控和异常监控。 1、数据监控 主要是为了收集跟用户相关的数据,例如用户设备类型、浏览器版本、页面浏览量(…...

webstorm 创建运行纯Typescript项目
创建一个空项目,在项目根目录创建一个tsconfig.json文件自动配置: 打开终端输入tsc --init,即可自动生成tsconfig.json文件手动配置: 在项目根目录下新建一个tsconfig.json文件,并配置如下内容 具体配置可以直接使用下面的配置&am…...

GO-接口
1. 接口 在Go语言中接口(interface)是一种类型,一种抽象的类型。 interface是一组method的集合,接口做的事情就像是定义一个协议(规则),只要一台机器有洗衣服和甩干的功能,我就称它…...

【C语言】动态内存管理常用函数
前言 我们在之前学习的数组开辟的空间是固定不变的,有时候我们需要的空间⼤⼩在程序运⾏的时候才能知道~ c语言中的动态内存开辟,让程序员⾃⼰可以根据实际需求申请和释放相应空间,这使得空间的开辟变得灵活了许多。 欢迎关注个人主页&#x…...

【OpenGL】(1) 专栏介绍:OpenGL 库 | 3D 计算机图形应用 | GPGPU 计算 | 3D 建模和 3D动画 | 渲染技术介绍
🔗 《C语言趣味教程》👈 猛戳订阅!!! 💭 写在前面:本专栏主要内容是关于 3D 计算机图形技术的学习,重点是学习与此技术相关的 3D 实时渲染 (3D real-time rendering) 技术。我们会以…...

(二)TensorRT-LLM | 模型导出(v0.20.0rc3)
0. 概述 上一节 对安装和使用有个基本介绍。根据这个 issue 的描述,后续 TensorRT-LLM 团队可能更专注于更新和维护 pytorch backend。但 tensorrt backend 作为先前一直开发的工作,其中包含了大量可以学习的地方。本文主要看看它导出模型的部分&#x…...
将对透视变换后的图像使用Otsu进行阈值化,来分离黑色和白色像素。这句话中的Otsu是什么意思?
Otsu 是一种自动阈值化方法,用于将图像分割为前景和背景。它通过最小化图像的类内方差或等价地最大化类间方差来选择最佳阈值。这种方法特别适用于图像的二值化处理,能够自动确定一个阈值,将图像中的像素分为黑色和白色两类。 Otsu 方法的原…...
linux 错误码总结
1,错误码的概念与作用 在Linux系统中,错误码是系统调用或库函数在执行失败时返回的特定数值,用于指示具体的错误类型。这些错误码通过全局变量errno来存储和传递,errno由操作系统维护,保存最近一次发生的错误信息。值得注意的是,errno的值在每次系统调用或函数调用失败时…...

《基于Apache Flink的流处理》笔记
思维导图 1-3 章 4-7章 8-11 章 参考资料 源码: https://github.com/streaming-with-flink 博客 https://flink.apache.org/bloghttps://www.ververica.com/blog 聚会及会议 https://flink-forward.orghttps://www.meetup.com/topics/apache-flink https://n…...
JDK 17 新特性
#JDK 17 新特性 /**************** 文本块 *****************/ python/scala中早就支持,不稀奇 String json “”" { “name”: “Java”, “version”: 17 } “”"; /**************** Switch 语句 -> 表达式 *****************/ 挺好的ÿ…...
Caliper 配置文件解析:config.yaml
Caliper 是一个区块链性能基准测试工具,用于评估不同区块链平台的性能。下面我将详细解释你提供的 fisco-bcos.json 文件结构,并说明它与 config.yaml 文件的关系。 fisco-bcos.json 文件解析 这个文件是针对 FISCO-BCOS 区块链网络的 Caliper 配置文件,主要包含以下几个部…...
Redis:现代应用开发的高效内存数据存储利器
一、Redis的起源与发展 Redis最初由意大利程序员Salvatore Sanfilippo在2009年开发,其初衷是为了满足他自己的一个项目需求,即需要一个高性能的键值存储系统来解决传统数据库在高并发场景下的性能瓶颈。随着项目的开源,Redis凭借其简单易用、…...

基于PHP的连锁酒店管理系统
有需要请加文章底部Q哦 可远程调试 基于PHP的连锁酒店管理系统 一 介绍 连锁酒店管理系统基于原生PHP开发,数据库mysql,前端bootstrap。系统角色分为用户和管理员。 技术栈 phpmysqlbootstrapphpstudyvscode 二 功能 用户 1 注册/登录/注销 2 个人中…...

何谓AI编程【02】AI编程官网以优雅草星云智控为例建设实践-完善顶部-建立各项子页-调整排版-优雅草卓伊凡
何谓AI编程【02】AI编程官网以优雅草星云智控为例建设实践-完善顶部-建立各项子页-调整排版-优雅草卓伊凡 背景 我们以建设星云智控官网来做AI编程实践,很多人以为AI已经强大到不需要程序员了,其实不是,AI更加需要程序员,普通人…...

EasyRTC音视频实时通话功能在WebRTC与智能硬件整合中的应用与优势
一、WebRTC与智能硬件整合趋势 随着物联网和实时通信需求的爆发式增长,WebRTC作为开源实时通信技术,为浏览器与移动应用提供免插件的音视频通信能力,在智能硬件领域的融合应用已成必然趋势。智能硬件不再局限于单一功能,对实时…...