前端必备:高效处理树形数据与数组的实用函数

news2024/11/28 22:53:21

​🌈个人主页:前端青山
🔥系列专栏:Vue篇
🔖人终将被年少不可得之物困其一生

依旧青山,本期给大家带来Vuet篇专栏内容:Vue-树形数据处理|数组:实用函数封装

大家好,依旧青山,在开发项目过程中,前端对于数据的处理往往会封装一些公共的函数来提高工作效率和复用性,那么我给大家列几个数据处理函数封装

目录

数组添加键值对

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

数组转换为树结构

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

合并两数组转树形结构

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

数组列值组合字符串

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

树形结构查找节点

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

单条数据权限验证

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

树转列表

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

深拷贝对象|数组

功能概述

接收参数:

功能描述:

示例:

注意事项:

返回值:

总结

数组添加键值对

  • 给数组里面的每个object元素添加新的key值,

export function addKeysToData(arr, newKeys, froms) {
    if (Array.isArray(arr)) {
        arr.map((ele) => {
            for (let i = 0; i < newKeys.length; i++) {
                Vue.set(ele, newKeys[i], ele[froms[i]])
            }
            return ele
        })
    }
    return arr
}

功能概述

接收参数:
  • arr: 需要修改的数据数组。

  • newKeys: 要添加的新键名数组。

  • froms: 原数据中对应值的键名数组。

功能描述:
  1. 遍历数组: 遍历arr中的每个对象。

  2. 添加新键值对: 对于每个对象,根据newKeysfroms数组中的对应索引,从对象中获取值并添加新的键值对。

  3. 使用Vue.set方法: 使用Vue的Vue.set方法动态添加新键值对,确保响应式更新。

示例:
  • 原始数组:

    • [{"id":1,"name":"张三"},{"id":2,"name":"李四"}]

  • 调用函数:

    • addKeysToData(arr, ["userId","userName"], ["id","name"])

  • 返回结果:

    • 结果将是:

      javascript[
        {"id":1,"name":"张三","userId":1,"userName":"张三"},
        {"id":2,"name":"李四","userId":2,"userName":"李四"}
      ]

注意事项:
  • 使用Vue.set方法是为了确保Vue能够检测到新添加的属性,从而触发视图更新。

  • 如果不需要Vue的响应式特性,可以使用Object.defineProperty方法替代Vue.set

返回值:
  • 返回修改后的数组arr

数组转换为树结构

将数组根据key值转换为有层级的树结构数组,必须有id属性

export function arrayToTree(arr, key = 'parent_id', needSort = true, type = 'id') {
    let tree = [] //最后生成的树列表
​
​
    当为公司列表数据时,对本部数据进行处理,因为id有重复,则将带有本部的数据id加上'-1'
    for (let i = 0; i < arr.length; i++) {
        if (arr[i].name && (arr[i].name.indexOf("(本部)") != -1 || arr[i].name.indexOf("(本部)") != -1)) {
            arr[i].id += "-1";
        }
    }
    //查找一级节点
    let deleteIndexArr = []
    for (let i = 0; i < arr.length; i++) {
        let ele = arr[i]
        //如果是一节节点,直接插入tree列表
        if (!ele[key]) {
            tree.push(ele)
            deleteIndexArr.push(i)
        } else {
            let parentExist = false
            for (let j = 0; j < arr.length; j++) {
                if (ele[key] == arr[j].id) {
​
                    parentExist = true
                    break
                }
            }
            //如果在数组中不存在父节点,则在当前树中为1及节点
            if (!parentExist) {
                tree.push(ele)
                deleteIndexArr.push(i)
            }
        }
    }
    //在列表中删除一级节点
    for (let i = deleteIndexArr.length - 1; i >= 0; i--) {
        let index = deleteIndexArr[i]
        arr.splice(index, 1)
    }
    //使用完后,设置为空
    deleteIndexArr = null
​
    //循环遍历建树,直接数组为空,为防止数据错误导致死循环,暂时循环10次后退出
    let times = 0
    while (arr.length > 0 && times < 10) {
        times++
        let len = arr.length
        for (let i = 0; i < len; i++) {
            let ele = arr[i]
​
            let parentItem = findParent(tree, ele, key)
            //如果找到其父节点
            if (parentItem) {
                //如父节点已有子列表,则将当前节点插入父节点的childrenlist中
                if (parentItem.childrenList) {
                    parentItem.childrenList.push(ele)
                }
                //如果还没有子列表,创建childrenList,并将元素插入其中
                else {
                    if (!parentItem.children) {
                        Vue.set(parentItem, "children", 1);
                    }
​
                    Vue.set(parentItem, "childrenList", []);
                    parentItem.childrenList.push(ele);
                }
                arr.splice(i, 1)
                len--
                i--
            }
​
        }
    }
​
    //将找不到父节点的数据直接加入一级节点
    if (arr.length > 0) {
        tree.push(...arr)
    }
​
    function sort(eles){
        eles.sort((a, b) => a[type] < b[type] ? -1 : 1)
        eles.forEach(val => {
            if(val.childrenList && val.childrenList.length > 0){
                sort(val.childrenList)
            }
        })
    }
​
    if (needSort) {
        sort(tree)
    }
​
    return tree
}

功能概述

接收参数:
  • arr: 需要转换为树形结构的原始数组。

  • key: 指定作为父节点ID的属性名,默认为"parent_id"

  • needSort: 是否需要对树进行排序,默认为true

  • type: 排序依据的属性名,默认为"id"

功能描述:
  1. 处理特殊数据: 如果数组中的某个元素的name属性包含"(本部)"或"(本部)",则在其id属性后加上"-1"

  2. 查找一级节点: 找出没有父节点的元素,即一级节点,并将它们添加到树形结构中。

  3. 构建树形结构: 循环遍历数组,为每个元素找到其父节点,并将其添加到父节点的子节点列表中。

  4. 处理剩余元素: 如果循环结束后仍有元素未被添加到树中,则将这些元素视为一级节点添加到树中。

  5. 排序树形结构: 如果needSorttrue,则对整个树形结构进行排序。

示例:
  • 原始数组:

    • [{"id":1,"name":"部门A"},{"id":2,"name":"部门B","parent_id":1},{"id":3,"name":"小组X","parent_id":2},{"id":4,"name":"小组Y","parent_id":1}]

  • 调用函数:

    • arrayToTree(arr)

  • 返回结果:

    • 结果将是一个树形结构,类似于:

      javascript[
        {"id":1,"name":"部门A","childrenList":[{"id":2,"name":"部门B"},{"id":4,"name":"小组Y"}]},
        {"id":2,"name":"部门B","childrenList":[{"id":3,"name":"小组X"}]}
      ]

注意事项:
  • 函数假设输入的数组中的元素具有正确的parent_id信息,以构建出正确的树形结构。

  • 如果needSorttrue,则会对树形结构进行排序,排序依据为type属性。

返回值:
  • 返回一个树形结构的数组,其中包含了原始数组中的所有数据,并且按照层级关系组织。

合并两数组转树形结构

将两个数组合并成一个数组,并根据key值转换为有层级的树结构数组,必须有id属性,两个数组分别来自不同数据源,因此ID可能有重复,第二个数组仅只能包含最末级子节点

export function twoArrayToTree(arr1, arr2, key = "parent_id") {
    //先处理第二个数据,给id加上唯一标识
    for (let i = 0; i < arr2.length; i++) {
        arr2[i].id = 'c' + arr2[i].id
    }
    let arr = []; //临时数组,合并arr1和arr2
    arr.push(...arr1);
    //对父节点进行排序
    arr.sort((a, b) => {
        return a.id < b.id ? 1 : -1
    });
    //子节点不排序并反序后插入,目的是为了最终的树按照原先的顺序返回,
    arr.push(...arr2.reverse());
    let tree = arrayToTree(arr, key, false); //最后生成的树列表
​
    //去除掉第二个数组id前的标识
    for (let i = 0; i < arr2.length; i++) {
        arr2[i].id = arr2[i].id.substring(1)
    }
    return tree;
}

功能概述

接收参数:
  • arr1: 第一个数据数组,通常包含根节点或顶级节点。

  • arr2: 第二个数据数组,通常包含子节点或其他层级的节点。

  • key: 指定作为父节点ID的属性名,默认为"parent_id"

功能描述:
  1. 处理第二个数组: 给arr2中的每个对象的id属性前加上"c"作为唯一标识。

  2. 合并数组: 将arr1arr2合并到一个新的数组arr中。

  3. 排序父节点: 对合并后的数组arr中的父节点按id进行降序排序。

  4. 插入子节点: 将arr2反向排序后插入到arr中。这样可以确保子节点按照原始顺序被正确地插入到父节点下。

  5. 转换为树结构: 使用arrayToTree函数将合并后的数组转换成树形结构。

  6. 移除标识: 最后移除arr2中每个对象id前的"c"标识。

示例:
  • 原始数组:

    • arr1:

      [{"id":1,"name":"部门A"},{"id":2,"name":"部门B"}]

    • arr2:

      [{"id":3,"name":"小组X","parent_id":1},{"id":4,"name":"小组Y","parent_id":2}]

  • 调用函数:

    • twoArrayToTree(arr1, arr2)

  • 返回结果:

    • 结果将是一个树形结构,类似于:

      javascript[
        {"id":1,"name":"部门A","children":[{"id":"c3","name":"小组X"}]},
        {"id":2,"name":"部门B","children":[{"id":"c4","name":"小组Y"}]}
      ]

注意事项:
  • 函数假设输入的数组已经包含了正确的parent_id信息,以构建出正确的树形结构。

  • arrayToTree函数未在提供的代码片段中给出,需要确保它能够正确地将数组转换成树形结构。

返回值:
  • 返回一个树形结构的数组,其中包含了arr1arr2中的所有数据,并且按照层级关系组织。

数组列值组合字符串

获取数组对应列合并后的字符串,字符串用splitStr分割

export function getArrayColStrs(arr, colKey = 'id', splitStr = ',') {
    if (!arr || arr.length == 0) return '';
​
    return arr.map(e => e[colKey]).join(splitStr)
}

功能概述

接收参数:
  • arr: 需要处理的数组。

  • colKey: 指定从数组元素中提取的键名,默认为"id"

  • splitStr: 用于连接提取的值的分隔符,默认为,

功能描述:
  1. 检查数组: 如果arr为空或长度为0,则返回空字符串。

  2. 提取键值: 从数组中的每个元素中提取指定键colKey对应的值。

  3. 拼接字符串: 使用splitStr将提取的值连接成一个字符串。

示例:
  • 原始数组:

    • [{"id":1,"name":"张三"},{"id":2,"name":"李四"}]

  • 调用函数:

    • getArrayColStrs(arr, "id", ",")

  • 返回结果:

    • 结果将是:

      plaintext
      ​
      "1,2"

注意事项:
  • 如果数组中的元素缺少指定的键colKey,则相应的值将为undefined

返回值:
  • 返回一个字符串,其中包含了数组中所有元素的指定键值,使用splitStr分隔。

树形结构查找节点

在list数组中,根据id查找对应的节点

export function getNode(list, id) {
    let node = null;
    for (let i = 0; i < list.length; i++) {
        if (list[i].id == id) {
            node = list[i];
            break;
        }
        if (list[i].childrenList && list[i].childrenList.length > 0) {
            let item = getNode(list[i].childrenList, id);
            if (item != null) {
                node = item;
                break;
            }
        }
    }
    return node;
}

功能概述

接收参数:
  • list: 需要搜索的树形结构数组。

  • id: 需要查找的节点的ID。

功能描述:
  1. 遍历树: 从list开始,递归地遍历树形结构。

  2. 查找节点: 查找具有指定id的节点。

  3. 返回节点: 如果找到匹配的节点,则返回该节点;否则返回null

示例:
  • 树形结构:

    • javascript[
        {"id":1,"name":"部门A","childrenList":[{"id":2,"name":"部门B"},{"id":4,"name":"小组Y"}]},
        {"id":2,"name":"部门B","childrenList":[{"id":3,"name":"小组X"}]}
      ]

  • 调用函数:

    • getNode(tree, 3)

  • 返回结果:

    • 结果将是:

      javascript
      ​
      {"id":3,"name":"小组X"}

注意事项:
  • 函数假设输入的树形结构是有效的,即每个节点都有唯一的id

  • 如果树形结构中存在多个相同的id,函数只会返回第一个找到的匹配项。

返回值:
  • 返回一个对象,表示找到的节点;如果没有找到,则返回null

单条数据权限验证

判断选的数据是否仅有一条,且有权限

export function isOneData(selected, dataRight = null, msg) {
    if (selected.length > 1) {
        AnMsgbox.msgbox({ message: "一次仅能操作一条数据" });
        return false;
    }
    if (selected.length == 0) {
        AnMsgbox.msgbox({ message: "请选择需要操作的数据" });
        return false;
    }
    if (dataRight) {
        if (!selected[0].dataRight[dataRight] ||
            (selected[0].dataRight[dataRight] != "1" && selected[0].dataRight[dataRight] != "2")
        ) {
            AnMsgbox.msgbox({
                message: msg ?? "当前选择的数据无权限",
            });
            return false;
        }
    }
​
    return true;
}

功能概述

接收参数:
  • selected: 已选中的数据项数组。

  • dataRight: 可选参数,表示需要检查的数据权限键名。

  • msg: 可选参数,自定义消息文本。

功能描述:
  1. 检查数量: 确保selected数组中只有一条数据。

  2. 提示信息: 如果selected数组为空或超过一条数据,则显示提示信息并返回false

  3. 权限检查: 如果指定了dataRight,则检查第一条数据是否具有相应的权限。

  4. 返回结果: 如果通过所有检查,则返回true;否则返回false

示例:
  • 已选中数据:

    • javascript[
        {"id":1,"name":"张三","dataRight":{"edit":"1"}},
        {"id":2,"name":"李四","dataRight":{"edit":"0"}}
      ]

  • 调用函数:

    • isOneData([selected[0]], "edit")

  • 返回结果:

    • 结果将是:

      javascript
      ​
      true

注意事项:
  • 如果selected数组为空或超过一条数据,函数会显示提示信息。

  • 如果指定了dataRight且第一条数据不具有相应的权限,函数也会显示提示信息。

返回值:
  • 返回一个布尔值,表示是否满足条件。

树转列表

将tree转化为list,数据扁平化

export function treeToList(tree) {
    let res = []; // 用于存储递归结果(扁平数据)
    // 递归函数
    let fn = (source) => {
        source.forEach((el) => {
            res.push(el);
            el.children && el.children > 0 ? fn(el.childrenList) : ""; // 子级递归
        });
    };
    fn(tree);
    return res;
}

功能概述

接收参数:
  • tree: 需要转换的树形结构数组。

功能描述:
  1. 初始化结果数组: 创建一个空数组res用于存储扁平化的数据。

  2. 递归函数: 定义一个递归函数fn,用于遍历树形结构并将每个节点添加到结果数组中。

  3. 遍历树: 使用fn函数遍历整个树形结构。

  4. 返回结果: 返回扁平化后的数组res

示例:
  • 树形结构:

    • javascript[
        {"id":1,"name":"部门A","childrenList":[{"id":2,"name":"部门B"},{"id":4,"name":"小组Y"}]},
        {"id":2,"name":"部门B","childrenList":[{"id":3,"name":"小组X"}]}
      ]

  • 调用函数:

    • treeToList(tree)

  • 返回结果:

    • 结果将是:

      javascript[
        {"id":1,"name":"部门A"},
        {"id":2,"name":"部门B"},
        {"id":4,"name":"小组Y"},
        {"id":3,"name":"小组X"}
      ]

注意事项:
  • 函数假设输入的树形结构是有效的,即每个节点都有唯一的id

  • 如果树形结构中存在多个相同的id,函数不会处理这种情况。

  • 函数假设每个节点的子节点列表键名为childrenList

返回值:
  • 返回一个扁平化的数组,包含了原树形结构中的所有节点。

深拷贝对象|数组

深拷贝 传入数组或对象

export function deepClone(obj) {
    if (obj === null || typeof obj !== 'object') {
        return obj;
    }

    if (Array.isArray(obj)) {
        const arrCopy = [];
        for (let i = 0; i < obj.length; i++) {
            arrCopy[i] = deepClone(obj[i]);
        }
        return arrCopy;
    }

    const objCopy = {};
    for (const key in obj) {
        if (obj.hasOwnProperty(key)) {
            objCopy[key] = deepClone(obj[key]);
        }
    }

    return objCopy;
}

功能概述

接收参数:
  • obj: 需要深拷贝的对象。

功能描述:
  1. 基础类型处理: 如果obj不是对象或已经是null,则直接返回obj

  2. 数组处理: 如果obj是数组,则创建一个新的数组并递归地深拷贝每个元素。

  3. 对象处理: 如果obj是对象,则创建一个新的对象并递归地深拷贝每个属性。

  4. 返回结果: 返回深拷贝后的对象或数组。

示例:
  • 原始对象:

    • javascript{
        a: 1,
        b: [1, 2, 3],
        c: { x: 10, y: 20 },
        d: null,
        e: undefined,
        f: function() { console.log("Hello"); }
      }

  • 调用函数:

    • deepClone(originalObj)

  • 返回结果:

    • 结果将是:

      javascript{
        a: 1,
        b: [1, 2, 3],
        c: { x: 10, y: 20 },
        d: null,
        e: undefined,
        f: [Function: f]
      }

注意事项:
  • 函数支持基本类型、数组和对象的深拷贝。

  • 函数不支持循环引用的对象。

  • 函数不深拷贝函数类型的属性。

返回值:
  • 返回一个深拷贝后的对象或数组。

总结

  1. 数组添加键值对 (addKeysToData):

    • 为数组中的每个对象添加新的键值对。

    • 使用 Vue.set 方法确保 Vue 的响应式更新。

  2. 数组转换为树结构 (arrayToTree):

    • 将一维数组转换为树形结构。

    • 支持对树形结构进行排序。

  3. 合并两数组转树形结构 (twoArrayToTree):

    • 将两个数组合并,并转换为树形结构。

    • 处理 ID 重复问题,适用于两个不同的数据源。

  4. 数组列值组合字符串 (getArrayColStrs):

    • 获取数组中特定键的所有值,并用指定分隔符连接成字符串。

  5. 树形结构查找节点 (getNode):

    • 在树形结构中根据 ID 查找指定节点。

  6. 单条数据权限验证 (isOneData):

    • 验证用户选择的数据是否仅有一条,并且用户对该数据有操作权限。

  7. 树转列表 (treeToList):

    • 将树形结构转换为扁平化的列表。

  8. 深拷贝对象或数组 (deepClone):

    • 实现对象或数组的深拷贝功能。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2062342.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

3、springboot时代背景

一、微服务 二、分布式 三、云原生 原生应用如何上云。 Cloud Native 上云的困难 服务自愈弹性伸缩服务隔离自动化部署灰度发布流量治理...... 上云的解决

人工智能算法工程师(中级)课程21-深度学习中各种优化器算法的应用与实践、代码详解

大家好&#xff0c;我是微学AI&#xff0c;今天给大家介绍一下人工智能算法工程师(中级)课程21-深度学习中各种优化器算法的应用与实践、代码详解。本文将介绍PyTorch框架下的几种优化器&#xff0c;展示如何使用PyTorch中的优化器&#xff0c;我们将使用MNIST数据集和一个简单…

云游戏畅玩黑神话悟空:使用 NVIDIA 4090 体验极致画质

​ 黑神话悟空 爽啦&#xff01;没有好配置又想玩《黑神话&#xff1a;悟空》的朋友们都爽啦&#xff01;自己没有好的 GPU&#xff0c;体验《黑神话&#xff1a;悟空》时画质不好玩的不舒心&#xff1f;厚德云来帮你解决问题&#xff01;厚德云上线了《黑神话&#xff1a;悟空…

机器学习第五十三周周报 MAG

文章目录 week53 MAG摘要Abstract1. 题目2. Abstract3. 预测标准3.1 问题提出3.2 数据预处理3.3 模型架构MAG3.4 时域故障模式识别3.5 故障检测器 4. 文献解读4.1 Introduction4.2 创新点4.3 实验过程4.4 实验结果4.5 结果分析 5. 结论小结参考文献 week53 MAG 摘要 本周阅读…

【ASPLOS2024】RECom:通过编译器技术加速推荐模型推理,论文中选并获得荣誉奖项!

2024年5月&#xff0c;关于推荐模型自动编译优化的论文《RECom: A Compiler Approach to Accelerate Recommendation Model Inference with Massive Embedding Columns》在系统领域顶会ASPLOS 2024上中选并进行了展示&#xff0c;并被授予了Distinguished Artifact Award 荣誉&…

基于springboot的招聘系统的设计与实现

TOC springboot614基于springboot的招聘系统的设计与实现--论文 研究背景 近年来&#xff0c;由于计算机技术和互联网技术的快速发展&#xff0c;使得所有企事业单位内部都是数字化、信息化、无纸化的发展趋势&#xff0c;随着趋势的发展&#xff0c;各种决策系统、辅助系统…

springboot安全在线学习平台---附源码131019

摘 要 这是采用springboot技术&#xff0c;SQL Server数据库实现的一个基于网络的在线学习系统。系统具有用户登录和注册、普通用户、课程分类、课程、购买表、课程上传等功能。在线学习是通过提供电子课件&#xff0c;让学生可以进行在线学习&#xff0c;并支持电子课件下载的…

windows主机查询url请求来自哪里发起的

最近使用fiddler抓包&#xff0c;看到一直有http://conna.gj.qq.com:47873 的请求&#xff0c; 对此进行溯源&#xff0c;确定是不是被攻击了。 在dos里查询端口进程&#xff1a;netstat -ano | findstr :47873 查到来自8020的进程id 查看此进程应用&#xff0c;发现竟然是…

postgresql 集群文档

https://www.cnblogs.com/Alicebat/p/14148933.html [命令] Pacemaker 命令 pcs cluster &#xff08;管理节点&#xff09; – Eternal Center PostgreSQL实战之物理复制和逻辑复制&#xff08;五&#xff09;_postgresql 流复制和物理复制-CSDN博客 https://jingyan.baidu…

UE5.4 - 下载和安装

一. 简介 虚幻引擎&#xff08;Unreal Engine&#xff09;是由 Epic Games 公司推出的一款功能强大的游戏开发引擎。它于 1998 年推出第一代&#xff0c;其口号是 “全球最开放、最先进的实时 3D 创作工具”。 虚幻引擎被广泛应用于游戏产业&#xff0c;创作出了众多知名的 3…

企业级WEB应用服务器TOMCAT从讲解到实战一篇解决

一 .WEB技术 1.1 HTTP协议和B/S 结构 操作系统有进程子系统&#xff0c;使用多进程就可以充分利用硬件资源。进程中可以多个线程&#xff0c;每一个线程可以 被CPU调度执行&#xff0c;这样就可以让程序并行的执行。这样一台主机就可以作为一个服务器为多个客户端提 供计算服…

教程:postman的平替hoppscotch,又叫postwoman,hoppscotch的docker-compose安装过程

目录 1. 背景2. 前期准备2.1 准备docker-compose文件&#xff0c;两个版本&#xff0c;一个3合1&#xff0c;一个分开2.1.1 3合1版本&#xff08;推荐&#xff09;2.1.2 独立版本 2.2 准备安装nginx-proxy-manager&#xff08;可选&#xff09;2.2 准备.env文件2.2.1 默认ip的.…

爬虫案例5——爬取东方财富网的港股数据

简介&#xff1a;个人学习分享&#xff0c;如有错误&#xff0c;欢迎批评指正 任务&#xff1a;从东方财富网中爬取港股的代码&#xff0c;名称&#xff0c;最近价格&#xff0c;涨跌幅&#xff0c;今开&#xff0c;最高等数据 目标网页地址&#xff1a;https://data.eastmone…

科技大厂对AI的垄断

每周跟踪AI热点新闻动向和震撼发展 想要探索生成式人工智能的前沿进展吗&#xff1f;订阅我们的简报&#xff0c;深入解析最新的技术突破、实际应用案例和未来的趋势。与全球数同行一同&#xff0c;从行业内部的深度分析和实用指南中受益。不要错过这个机会&#xff0c;成为AI领…

探索HTML中的“iframe”标签——WEB开发系列12

现代网页开发中&#xff0c;​​<iframe>​​ 标签是一个非常重要的工具。允许我们在一个网页中嵌入另一个网页&#xff0c;对于展示外部内容、应用嵌套或实现复杂的布局设计都非常有用。来一起探讨如何使用 ​​iframe​​ 标签&#xff0c;包括设置高度和宽度、移除边框…

记录 升级到Gradle 8.4.2 遇到的坑

序言 最近将Gradle从4.0.1 升级到 8.4.2 遇到了很多坑&#xff0c;记录下来帮助有缘人 升级gradle 修改根目录的build.gradle dependencies {classpath com.android.tools.build:gradle:8.4.2classpath org.jetbrains.kotlin:kotlin-gradle-plugin:1.9.0}修改gradle-wrapper.…

【html+css 绚丽Loading】000011 三元轮回珠

前言&#xff1a;哈喽&#xff0c;大家好&#xff0c;今天给大家分享htmlcss 绚丽Loading&#xff01;并提供具体代码帮助大家深入理解&#xff0c;彻底掌握&#xff01;创作不易&#xff0c;如果能帮助到大家或者给大家一些灵感和启发&#xff0c;欢迎收藏关注哦 &#x1f495…

【TS】函数重载的作用

前言 当调用一个函数时&#xff0c;通常会提示有多种调用方式&#xff0c;各种调用方式的参数类型、参数数量、返回值等均可能不同。本文通过自己封装的message作为案例模拟一下。 实现 自己封装的message组件&#xff0c;有以下7种调用方式 message({mode: "mode"…

QT-计算器

QT-计算器 一、演示效果二、关键程序三、下载链接 一、演示效果 二、关键程序 #include "mainwindow.h" #include "ui_mainwindow.h" #include <QDebug>MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow) {ui…

分布式事务:基本概念

文章目录 一、基础概念1、什么是事务2、本地事务3 、分布式事务4、分布式事务产生的场景 二、分布式事务基础理论1、CAP理论&#xff08;1&#xff09;理解CAP&#xff08;2&#xff09;CAP组合方式&#xff08;3&#xff09;总结 2、BASE理论 三、分布式事务解决方案之2PC&…