element ui 表格组件与分页组件的二次封装
目录
组件封装
parseTime函数
debounce 函数
页面使用
【扩展】vue 函数式组件
函数式组件特点:
函数式组件的优点:
【扩展】vue中的render函数
一、初步认识render函数
二、为什么使用render函数
三、render函数的解析
组件封装
这段代码是一个封装的分页表格组件。它使用了Vue.js框架,并结合了Element UI中的el-table和el-pagination组件来实现。该组件接受一系列属性作为数据源,包括列表数据(list)、表格列(columns)、操作按钮列(operates)、总数(total)、分页参数(pagination)等。
在模板中,使用el-table组件来展示表格数据,使用el-pagination组件来实现分页功能。el-table-column用来定义每列的样式和展示内容。组件中还包括其他的一些方法和事件处理函数,如handleSizeChange用于切换每页显示的数量,handleIndexChange用于切换页码,handleSelectionChange处理多行选中等。
此外,还定义了一些样式规则来美化表格的显示效果,如设置表头颜色、调整列的样式、设置操作按钮组的布局、设置筛选弹窗和表格操作弹窗的样式等。
最后,使用了scss来编写样式表,通过设置类名来控制样式的展示。
-
在
<template>
标签中,定义了一个表格组件,包括表格本身,列定义,按钮操作组,和分页控件。 -
在
<script>
标签中,导入了必要的依赖,并定义了组件的属性(props)、数据(data)、生命周期钩子(activated、beforeDestroy、deactivated、created、mounted)和方法(methods)。 -
props
属性用于接受从父组件传递进来的数据,如数据列表list
、列定义columns
、按钮操作operates
、总数total
、分页参数pagination
等。 -
data
数据属性包括一些内部状态,如表格高度height
、监听窗口调整大小的回调函数$_resizeHandler
、当前页码pageIndex
、表格分页信息tableCurrentPagination
、多行选中数据multipleSelection
等。 -
在生命周期钩子中,组件监听窗口大小调整事件,自动调整表格高度,并在适当的生命周期中初始化和销毁事件监听器。
-
methods
包括一系列方法,如计算表头宽度的方法headSpanFit
、初始化事件监听器的方法initListener
、销毁事件监听器的方法destroyListener
、调整表格高度的方法resize
、处理每页显示数量变化的方法handleSizeChange
、处理页码变化的方法handleIndexChange
、处理多行选中的方法handleSelectionChange
等。 -
最后,在
<style>
标签中定义了一些样式,包括表格样式、分页样式、按钮样式、筛选和操作弹窗样式等。
<!--region 封装的分页 table-->
<!--region 封装的分页 table-->
<template><div class="table"><el-table id="iTable" v-loading.iTable="options.loading" :data="list" :stripe="options.stripe" ref="mutipleTable"@selection-change="handleSelectionChange" :height="noStatic ? customHeight : height":max-height="noStatic ? customHeight : height"><!--region 选择框--><el-table-column v-if="options.mutiSelect" type="selection" style="width: 55px"></el-table-column><!--endregion--><!--region 数据列--><template v-for="(column, index) in columns"><el-table-column :min-width="headSpanFit(column)" :prop="column.prop" :label="column.label" :align="column.align":width="column.width"><template slot-scope="scope"><template v-if="!column.render"><template v-if="column.formatter"><span v-html="column.formatter(scope.row, column)"></span></template><template v-else><span>{{ scope.row[column.prop] === 0? 0: scope.row[column.prop] || "--" }}</span></template></template><template v-else><expand-dom :column="column" :row="scope.row" :render="column.render" :index="index"></expand-dom></template></template></el-table-column></template><!--endregion--><!--region 按钮操作组--><el-table-column ref="fixedColumn" label="操作" align="center" :width="operates.width" :fixed="operates.fixed"v-if="operates.list.length > 0"><template slot-scope="scope"><div class="operate-group"><template v-for="(btn, key) in operates.list"><div class="item" v-if="typeof btn.show == 'function'? btn.show(scope.$index, scope.row): btn.show"><el-button :type="btn.type" :key="key + 'itbtn'" :size="btn.size || 'mini'" :icon="btn.icon" :disabled="typeof btn.disabled == 'function'? btn.disabled(scope.$index, scope.row): btn.disabled" :plain="btn.plain" @click.native.prevent="btn.method(scope.$index, scope.row)">{{btn.label }}</el-button></div></template></div></template></el-table-column><!--endregion--></el-table><div style="height: 12px"></div><!--region 分页--><el-pagination v-if="pagination" @size-change="handleSizeChange" @current-change="handleIndexChange":page-size="tableCurrentPagination.pageSize" :page-sizes="this.tableCurrentPagination.pageArray":current-page="tableCurrentPagination.pageIndex" layout="total,sizes, prev, pager, next,jumper":total="total"></el-pagination><!--endregion--></div>
</template>
<!--endregion-->
<script>
import { debounce } from "@/utils";
const _pageArray = [20, 50, 100]; // 每页展示条数的控制集合
export default {props: {list: {type: Array,default: [], // prop:表头绑定的地段,label:表头名称,align:每列数据展示形式(left, center, right),width:列宽}, // 数据列表columns: {type: Array,default: [], // 需要展示的列 === prop:列数据对应的属性,label:列名,align:对齐方式,width:列宽},operates: {type: Object,default: {}, // width:按钮列宽,fixed:是否固定(left,right),按钮集合 === label: 文本,type :类型(primary / success / warning / danger / info / text),show:是否显示,icon:按钮图标,plain:是否朴素按钮,disabled:是否禁用,method:回调方法},total: {type: Number,default: 0,}, // 总数pagination: {type: Object,default: null, // 分页参数 === pageSize:每页展示的条数,pageIndex:当前页,pageArray: 每页展示条数的控制集合,默认 _page_array},noStatic: false, // 是否计算表格高度customHeight: {//与noStatic一起使用type: Number,default: 320,},otherHeight: {type: Number,default: 180,}, // 计算表格的高度options: {type: Object,default: {stripe: false, // 是否为斑马纹 tableloading: false, // 是否添加表格loading加载动画highlightCurrentRow: false, // 是否支持当前行高亮显示mutiSelect: false, // 是否支持列表项选中功能},}, // table 表格的控制参数},components: {expandDom: {functional: true,props: {row: Object,render: Function,index: Number,column: {type: Object,default: null,},},render: (h, ctx) => {const params = {row: ctx.props.row,index: ctx.props.index,};if (ctx.props.column) params.column = ctx.props.column;return ctx.props.render(h, params);},},},data() {return {height: 250,$_resizeHandler: null,pageIndex: 1,tableCurrentPagination: {},multipleSelection: [], // 多行选中};},activated() {// 通常是在使用 Vue.js 的 <keep-alive> 包装时,组件会被缓存并在重新激活时调用这个钩子函数。if (!this.$_resizeHandler) {// avoid duplication initthis.initListener();}// when keep-alive chart activated, auto resizethis.resize();},//当组件即将被销毁(beforeDestroy)时,会调用这个钩子函数。beforeDestroy() {this.destroyListener();},//当组件被停用(deactivated),通常也是在 <keep-alive> 包装下,组件会调用这个钩子函数。deactivated() {this.destroyListener();},created() { },mounted() {this.initListener();if (this.pagination && !this.pagination.pageSizes) {this.pagination.pageArray = _pageArray; // 每页展示条数控制}this.tableCurrentPagination = this.pagination || {pageSize: this.total,pageIndex: 1,}; // 判断是否需要分页},methods: {//计算小列宽headSpanFit(column) {let labelLong = column.label.length; // 表头label长度let size = 20; // 根据需要定义标尺,直接使用字体大小确定就行,也可以根据需要定义let minWidth = labelLong * size < 100 ? 100 : labelLong * size; // 根据label长度计算该表头最终宽度return minWidth;},// 初始化监听器的方法。initListener() {this.$_resizeHandler = debounce(() => {this.resize();}, 200);window.addEventListener("resize", this.$_resizeHandler);this.$nextTick(() => {this.resize();});},//这是一个销毁监听器的方法。destroyListener() {window.removeEventListener("resize", this.$_resizeHandler);this.$_resizeHandler = null;},//计算表格的高度resize() {// 不需要计算if (this.noStatic) {return;}const { mutipleTable } = this.$refs;// 窗口的高度减去表格的顶部偏移let staticHeight =window.innerHeight - this.$refs.mutipleTable.$el.offsetTop - this.otherHeight;this.height = staticHeight < 250 ? 250 : staticHeight;console.log(this.height);//保表格的布局在高度调整后得以更新。mutipleTable && mutipleTable.doLayout();},// 切换每页显示的数量handleSizeChange(size) {if (this.pagination) {this.tableCurrentPagination = {pageIndex: 1,pageSize: size,};this.$emit("handleSizeChange", this.tableCurrentPagination);}},// 切换页码handleIndexChange(currnet) {if (this.pagination) {this.tableCurrentPagination.pageIndex = currnet;this.$emit("handleIndexChange", this.tableCurrentPagination);}},// 多行选中handleSelectionChange(val) {this.multipleSelection = val;this.$emit("handleSelectionChange", val);},// 显示 表格操作弹窗showActionTableDialog() {this.$emit("handelAction");},},
};
</script><style lang="scss">
.table {height: 100%;.el-pagination {float: right;margin: 20px;}.el-table__header-wrapper,.el-table__fixed-header-wrapper {thead {tr {th {color: #333333;}}}}.el-table-column--selection .cell {padding: 0;text-align: center;}.el-table__fixed-right {bottom: 0 !important;right: 6px !important;z-index: 1004;}.operate-group {display: flex;flex-wrap: wrap;.item {margin-top: 4px;margin-bottom: 4px;display: block;flex: 0 0 50%;}}.filter-data {top: e("calc((100% - 100px) / 3)");background-color: rgba(0, 0, 0, 0.7);}.table-action {top: e("calc((100% - 100px) / 2)");background-color: rgba(0, 0, 0, 0.7);}.fix-right {position: absolute;right: 0;height: 100px;color: #ffffff;width: 30px;display: block;z-index: 1005;writing-mode: vertical-rl;text-align: center;line-height: 28px;border-bottom-left-radius: 6px;border-top-left-radius: 6px;cursor: pointer;}
}
</style>
parseTime函数
// 日期格式化
export function parseTime(time, pattern) {if (arguments.length === 0 || !time) {return null}const format = pattern || '{y}-{m}-{d} {h}:{i}:{s}'let dateif (typeof time === 'object') {date = time} else {if ((typeof time === 'string') && (/^[0-9]+$/.test(time))) {time = parseInt(time)} else if (typeof time === 'string') {time = time.replace(new RegExp(/-/gm), '/').replace('T', ' ').replace(new RegExp(/\.[\d]{3}/gm), '');}if ((typeof time === 'number') && (time.toString().length === 10)) {time = time * 1000}date = new Date(time)}const formatObj = {y: date.getFullYear(),m: date.getMonth() + 1,d: date.getDate(),h: date.getHours(),i: date.getMinutes(),s: date.getSeconds(),a: date.getDay()}const time_str = format.replace(/{(y|m|d|h|i|s|a)+}/g, (result, key) => {let value = formatObj[key]// Note: getDay() returns 0 on Sundayif (key === 'a') { return ['日', '一', '二', '三', '四', '五', '六'][value] }if (result.length > 0 && value < 10) {value = '0' + value}return value || 0})return time_str
}
debounce 函数
export function debounce(func, wait, immediate) {let timeout, args, context, timestamp, resultconst later = function() {// 据上一次触发时间间隔const last = +new Date() - timestamp// 上次被包装函数被调用时间间隔 last 小于设定时间间隔 waitif (last < wait && last > 0) {timeout = setTimeout(later, wait - last)} else {timeout = null// 如果设定为immediate===true,因为开始边界已经调用过了此处无需调用if (!immediate) {result = func.apply(context, args)if (!timeout) context = args = null}}}return function(...args) {context = thistimestamp = +new Date()const callNow = immediate && !timeout// 如果延时不存在,重新设定延时if (!timeout) timeout = setTimeout(later, wait)if (callNow) {result = func.apply(context, args)context = args = null}return result}
}
页面使用
<template><div class="table-page"><!--region table 表格--><app-table :list="list" :total="total" :otherHeight="otherHeight" :options="options" :pagination="pagination":columns="columns" :operates="operates" @handleSizeChange="handleSizeChange" @handleIndexChange="handleIndexChange"@handleSelectionChange="handleSelectionChange"></app-table><!--endregion--></div>
</template>
<script>
import {parseTime,} from "@/utils/ruoyi";
export default {data() {return {total: 0,list: [{id: 1,title: '标题',state: 0,author: '张三',phone: '12346788901',email: '1234556778@qq.com',createDate: "2023-04-23 16:11:38"}],otherHeight: 208,columns: [{prop: 'id',label: '编号',align: 'center',width: 60},{prop: 'title',label: '标题',align: 'center',width: 400,formatter: (row, column, cellValue) => {return `<span style="white-space: nowrap;color: dodgerblue;">${row.title}</span>`}},{prop: 'state',label: '状态',align: 'center',width: '160',render: (h, params) => {return h('el-tag', {props: { type: params.row.state === 0 ? 'success' : params.row.state === 1 ? 'info' : 'danger' } // 组件的props}, params.row.state === 0 ? '上架' : params.row.state === 1 ? '下架' : '审核中')}},{prop: 'author',label: '作者',align: 'center',width: 120},{prop: 'phone',label: '联系方式',align: 'center',width: 160},{prop: 'email',label: '邮箱',align: 'center',width: 240},{prop: 'createDate',label: '发布时间',align: 'center',width: 180,formatter: (row, column, cellValue) => {return parseTime(row.createDate)}}], // 需要展示的列operates: {width: 200,fixed: 'right',list: [{label: '编辑',type: 'warning',show: (index, row) => {return true},icon: 'el-icon-edit',plain: true,disabled: false,method: (index, row) => {this.handleEdit(index, row)}},{label: '删除',type: 'danger',icon: 'el-icon-delete',show: true,plain: false,disabled: (index, row) => {return false},method: (index, row) => {this.handleDel(index, row)}}]}, // 操作按钮组pagination: {pageIndex: 1,pageSize: 20}, // 分页参数options: {stripe: true, // 是否为斑马纹 tableloading: false, // 是否添加表格loading加载动画highlightCurrentRow: true, // 是否支持当前行高亮显示mutiSelect: true // 是否支持列表项选中功能} // table 的参数}},components: {expandDom: {props: {column: {required: true},row: {required: true}},render(h) {return h('div', {}, ([this.column.render(this.row, this.column)]))}}},mounted() {},methods: {// 切换每页显示的数量handleSizeChange(pagination) {this.pagination = pagination},// 切换页码handleIndexChange(pagination) {this.pagination = pagination},// 选中行handleSelectionChange(val) {console.log('val:', val)},// 编辑handleEdit(index, row) {console.log(' index:', index)console.log(' row:', row)},// 删除handleDel(index, row) {console.log(' index:', index)console.log(' row:', row)},}
}
</script>
【扩展】vue 函数式组件
函数式组件特点:
- 没有管理任何状态
- 没有监听任何传递给它的状态
- 没有生命周期方法
- 它只是接收一些
prop
的函
我们将这样的组件标记为functional
:
- 无状态 == 无响应式数据
- 无实例 == 无
this
上下文
函数式组件的优点:
- 渲染开销低,因为函数式组件只是函数;
{functional: true,// Props 是可选的props: {// ...},// 为了弥补缺少的实例// 提供第二个参数作为上下文render: function (createElement, context) {// ...}
}
props
: 提供所有prop
的对象children:VNode
子节点的数组slots
: 一个函数,返回了包含所有插槽的对象scoptedSlots
:(2.6.0) 一个暴露传入的作用域插槽的对象,也以函数形式暴露普通插槽data
:传递个组件的整个数据对象,作为createElement
的第二个参数传入组件parent
:对父组件的引用listeners
:(2.3.0+) 一个包含了:所有父组件为当前组件祖册的事件监听器对象,是data.on
的一个别名injections
:(2.3.0+) 如果使用了inject
选项,则改对象包含了:应当被注入的属性;
【扩展】vue中的render函数
一、初步认识render函数
import Vue from 'vue'
import App from './App'Vue.config.productionTip = falsenew Vue({el: '#app',render: h => h(App)
})
在使用脚手架创建vue项目的过程,我们很容易看到render这个函数,相对于其他标签,我们对于render还是比较陌生的,因此写下这篇文章你我共同理解。
二、为什么使用render函数
VUE推荐在绝大多数情况下使用template来创建我们的HTML。然而在一些场景中,我们真的需要JavaScript的完全编程的能力,这就是render函数,它比template更接近编译器。(这是官方的话)
简单来说,我们为什么要使用render函数呢?? 便是因为我们最经常使用的一个引入。
import Vue from "vue";
这一个引入你看似没有任何问题,但问题恰恰就是出在这。在不同版本的vue中,有vue.js和vue.runtime.xxx.js这两种js文件。其中
(1)vue.js是完整版的vue,包含核心功能+模板解析器。
(2)vue.runtime.xxx.js是运行版vue,只包含核心功能,没有模板解析器。
VUE开发者为了让我们打包的文件能尽可能小一点,在上述引入的是运行版vue。因为vue.runtime.xxx.js没有模板解析器,所以不能使用template配置项,这时候就需要使用render函数去接收到的createElement函数去指定具体内容,创建html模板。
三、render函数的解析
render 函数即渲染函数,它是个函数,它的参数 createElement 也是个函数。
上边的代码中 render: h => h(App) ,这是 ES6的箭头函数的写法,可以把 h 当作 createElement 的别名。所以这段代码其实相当于
render: function (createElement) {return createElement(App)
}
这个函数的作用就是生成一个 VNode节点,render 函数得到这个 VNode 节点之后,返回给 Vue.js 的 mount 函数,渲染成真实 DOM 节点,并挂载到根节点上。
createElement 函数的返回值是 VNode(即:虚拟节点)
createElement 函数的3个参数
- 一个 HTML 标签字符串,组件选项对象,或者解析上述任何一种的一个 async 异步函数。类型:String | Object | Function。必需。
- 一个包含模板相关属性的数据对象,你可以在 template 中使用这些特性。类型:Object。可选。
- 子虚拟节点 (VNodes),由 createElement() 构建而成,也可以使用字符串来生成“文本虚拟节点”。类型:String | Array。可选
new Vue({el: '#app',render:function (createElement) {//1.普通用法// createElement(标签,{属性},[内容])return createElement("h2",{class:"box"},['hello',createElement("button",["按钮"])])}
})
同时createElement也可以传进去一个组件,因此
render: h => h(App)
等同于
render:function (createElement) {return createElement(App)}
相关文章:

element ui 表格组件与分页组件的二次封装
目录 组件封装 parseTime函数 debounce 函数 页面使用 【扩展】vue 函数式组件 函数式组件特点: 函数式组件的优点: 【扩展】vue中的render函数 一、初步认识render函数 二、为什么使用render函数 三、render函数的解析 组件封装 这段代码是一…...

递归算法学习——有效的数独,解数独
一,有效的数独 1.题意 请你判断一个 9 x 9 的数独是否有效。只需要 根据以下规则 ,验证已经填入的数字是否有效即可。 数字 1-9 在每一行只能出现一次。数字 1-9 在每一列只能出现一次。数字 1-9 在每一个以粗实线分隔的 3x3 宫内只能出现一次。&#x…...

基于Alexnet深度学习网络的人员口罩识别算法matlab仿真
目录 1.算法运行效果图预览 2.算法运行软件版本 3.部分核心程序 4.算法理论概述 5.算法完整程序工程 1.算法运行效果图预览 2.算法运行软件版本 matlab2022a 3.部分核心程序 file_path1 test\mask\;% 图像文件夹路径 %获取测试图像文件夹下所有jpg格式的图像文件…...
【Java Web】利用Spring整合Redis,配置RedisTemplate
1. 在config中加入RedisConfig配置类 package com.nowcoder.community.config;import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.data.redis.connection.RedisConnectionFacto…...

如何正确的写出第一个java程序:hello java
1 前言 最近公司由于项目需要,开始撸java代码了。学习一门新的编程语言,刚开始总是要踩很多坑,所以记录一下学习过程,也希望对java初学者有所帮助。 2 hello java 2.1 程序源码 程序内容十分简单,这里就不再过多赘…...
使用llvm 编译最新的linux 内核(LoongArch)
1. 准备交叉工具链 llvm 使用了最新的llvm-17, 编译方法见:编译LoongArch的llvm交叉工具链 gcc 从linux 官方下载:http://mirrors.edge.kernel.org/pub/tools/crosstool/files/bin/x86_64/13.2.0/x86_64-gcc-13.2.0-nolibc-loongarch64-linux.tar.xz 发布llvm和g…...
Using Multiple RDF Knowledge Graphs for Enriching ChatGPT Responses
本文是LLM系列文章,针对《Using Multiple RDF Knowledge Graphs for Enriching ChatGPT Responses》的翻译。 使用多个RDF知识图来丰富ChatGPT响应 摘要1 引言2 相关工作3 GPT-LODS的过程和用例4 结束语 摘要 最近有一种趋势是使用新型人工智能聊天GPT聊天箱&…...
【Hive-小文件合并】Hive外部分区表利用Insert overwrite的暴力方式进行小文件合并
这里我们直接用实例来讲解,Hive外部分区表有单分区多分区的不同情况,这里我们针对不同情况进行不同的方式处理。 利用overwrite合并单独日期的小文件 1、单分区 # 开启此表达式:(sample_date)?. set hive.support.quoted.identifiersnon…...

位运算 |(按位或) (按位与) ^(按位异或)
目录 文章目录:本章讲解的主要是刷题系列 1:首先会介绍 I & ^这三个操作符的作用,性质 2:三道使用位运算操作符的经典 笔试题(来自剑指offer) 题目链接如下: 1:136. 只出现一次的数字 - 力扣(LeetCode…...

Qt应用开发(基础篇)——复选按钮 QCheckBox 单选按钮 QRadioButton
一、前言 QCheckBox类与QRadioButton类继承于QAbstractButton,QCheckBox是一个带有文本标签的复选框,QRadioButton是一个带有文本标签的单选按钮。 按钮基类 QAbstractButton QCheckBox QCheckBox复选框是一个很常用的控件,拥有开关(选中和未…...
AERMOD模型大气环境影响评价
随着我国经济快速发展,我国面临着日益严重的大气污染问题。近年来,严重的大气污染问题已经明显影响国计民生,引起政府、学界和人们越来越多的关注。大气污染是工农业生产、生活、交通、城市化等方面人为活动的综合结果,同时气象因…...
递归组装树结构的数据
开发中,经常遇到存在树形结构的数据,如行政区划这类数据,一级一级分层,后端需要组装好树形结构数据返回给前端。 由于返给前端的json数据中,如果是叶子节点了,说明它没有子节点,那么就没必要返…...

企业架构LNMP学习笔记7
PHP介绍: HTML:超文本标记语言 http: 超文本传输协议 端口80 浏览器将html代码解析成web页面。 PHP:超文本预处理器。后端语言开发,页面上需要动态改变修改的,需要连接数据库查询数据,转为html。 主要…...

开店星小程序上架教程和后台Request failed with status code 500[undefined]问题处理
开店星小程序上架教程和后台Request failed with status code 500[undefined]问题处理 刚刚安装好开店星网站后台之后都会出现这个code 500[undefined]的错误,需要改一下代码。改好了之后就可以正常使用了。如果大家不懂得这样处理的可以私聊我,帮忙处理…...
第一百三十六回 WillPopScope组件
文章目录 概念介绍使用方法示例代码 我们在上一章回中介绍了下拉刷新组件相关的内容,本章回中将介绍 WillPopScope组件.闲话休提,让我们一起Talk Flutter吧。 概念介绍 我们在本章回中介绍的WillPopScope组件是一种事件拦截类组件,它没有具…...
【论文爬虫】自动将论文详细信息直送notion并自动下载(含源码)
输入论文标题,本爬虫将自动在semanticscholar.com和arxiv.com搜索该文章,自动获取其日期、作者、url、摘要等信息,并自动发送到你提前设置好的notion数据库里,同时自动从arxiv下载论文,然后将论文的保存地址在notion页…...
Android知识点整理
关键点 Activity Fragment 调试应用 处理应用程序配置 Intent 和 Intent 过滤器 会使用Context 后台处理指南 Android 的数据隐私 Android 网络数据安全教程 Android 中的依赖项注入 内容提供程序 Android 内存管理概览 一些重要的库 1.Glide 是一个 Android 上的…...
JSON与电子表格
一、介绍 电子表格是一种常见的电子数据处理工具,而JSON是一种数据交换格式。电子表格和JSON之间可以进行数据的导入和导出,以实现数据的相互转换和交互。 在电子表格中,数据以行和列的形式组织,并可以包含不同的数据类型。每个…...
Oracle创建用户、授权视图权限
1、创建用户密码 create user 用户名 identified by 密码;2、创建视图 CREATE VIEW 用户1.表名1 AS SELECT * FROM 用户2.表名2 t;3、授权 GRANT SELECT ON 用户2.表名2 TO 用户1 with GRANT OPTION ;grant connect to 用户名; grant select on 用户1.表名1 t…...

MT4移动端应用指南:随时随地进行交易
如今,随着科技的不断发展,我们可以随时随地通过手机进行各种操作,包括进行金融交易。本文将为大家介绍一款优秀的金融交易软件——MT4(可在mtw.so/6gwPno这点下)移动端应用,并提供详细的使用指南࿰…...

装饰模式(Decorator Pattern)重构java邮件发奖系统实战
前言 现在我们有个如下的需求,设计一个邮件发奖的小系统, 需求 1.数据验证 → 2. 敏感信息加密 → 3. 日志记录 → 4. 实际发送邮件 装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其…...
rknn优化教程(二)
文章目录 1. 前述2. 三方库的封装2.1 xrepo中的库2.2 xrepo之外的库2.2.1 opencv2.2.2 rknnrt2.2.3 spdlog 3. rknn_engine库 1. 前述 OK,开始写第二篇的内容了。这篇博客主要能写一下: 如何给一些三方库按照xmake方式进行封装,供调用如何按…...

工业安全零事故的智能守护者:一体化AI智能安防平台
前言: 通过AI视觉技术,为船厂提供全面的安全监控解决方案,涵盖交通违规检测、起重机轨道安全、非法入侵检测、盗窃防范、安全规范执行监控等多个方面,能够实现对应负责人反馈机制,并最终实现数据的统计报表。提升船厂…...

【Redis技术进阶之路】「原理分析系列开篇」分析客户端和服务端网络诵信交互实现(服务端执行命令请求的过程 - 初始化服务器)
服务端执行命令请求的过程 【专栏简介】【技术大纲】【专栏目标】【目标人群】1. Redis爱好者与社区成员2. 后端开发和系统架构师3. 计算机专业的本科生及研究生 初始化服务器1. 初始化服务器状态结构初始化RedisServer变量 2. 加载相关系统配置和用户配置参数定制化配置参数案…...
测试markdown--肇兴
day1: 1、去程:7:04 --11:32高铁 高铁右转上售票大厅2楼,穿过候车厅下一楼,上大巴车 ¥10/人 **2、到达:**12点多到达寨子,买门票,美团/抖音:¥78人 3、中饭&a…...
Qwen3-Embedding-0.6B深度解析:多语言语义检索的轻量级利器
第一章 引言:语义表示的新时代挑战与Qwen3的破局之路 1.1 文本嵌入的核心价值与技术演进 在人工智能领域,文本嵌入技术如同连接自然语言与机器理解的“神经突触”——它将人类语言转化为计算机可计算的语义向量,支撑着搜索引擎、推荐系统、…...
全面解析各类VPN技术:GRE、IPsec、L2TP、SSL与MPLS VPN对比
目录 引言 VPN技术概述 GRE VPN 3.1 GRE封装结构 3.2 GRE的应用场景 GRE over IPsec 4.1 GRE over IPsec封装结构 4.2 为什么使用GRE over IPsec? IPsec VPN 5.1 IPsec传输模式(Transport Mode) 5.2 IPsec隧道模式(Tunne…...
2023赣州旅游投资集团
单选题 1.“不登高山,不知天之高也;不临深溪,不知地之厚也。”这句话说明_____。 A、人的意识具有创造性 B、人的认识是独立于实践之外的 C、实践在认识过程中具有决定作用 D、人的一切知识都是从直接经验中获得的 参考答案: C 本题解…...
动态 Web 开发技术入门篇
一、HTTP 协议核心 1.1 HTTP 基础 协议全称 :HyperText Transfer Protocol(超文本传输协议) 默认端口 :HTTP 使用 80 端口,HTTPS 使用 443 端口。 请求方法 : GET :用于获取资源,…...

使用LangGraph和LangSmith构建多智能体人工智能系统
现在,通过组合几个较小的子智能体来创建一个强大的人工智能智能体正成为一种趋势。但这也带来了一些挑战,比如减少幻觉、管理对话流程、在测试期间留意智能体的工作方式、允许人工介入以及评估其性能。你需要进行大量的反复试验。 在这篇博客〔原作者&a…...