当前位置: 首页 > article >正文

Golang——9、反射和文件操作

反射和文件操作

  • 1、反射
    • 1.1、reflect.TypeOf()获取任意值的类型对象
    • 1.2、reflect.ValueOf()
    • 1.3、结构体反射
  • 2、文件操作
    • 2.1、os.Open()打开文件
    • 2.2、方式一:使用Read()读取文件
    • 2.3、方式二:bufio读取文件
    • 2.4、方式三:os.ReadFile读取
    • 2.5、写入文件
    • 2.6、复制文件
    • 2.7、文件重命名
    • 2.8、创建目录
    • 2.9、删除目录和文件

1、反射

有时我们需要写一个函数,这个函数有能力统一处理各种值类型,而这些类型可能无法共享同一个接口, 也可能布局未知,也有可能这个类型在我们设计函数时还不存在,这个时候我们就可以用到反射。

空接口可以存储任意类型的变量,那我们如何知道这个空接口保存数据的类型是什么?值是什么呢?
1、可以使用类型断言
2、可以使用反射实现, 也就是在程序运行时动态的获取一个变量的类型信息和值信息。

Golang 中反射可以实现以下功能:
1、反射可以在程序运行期间动态的获取变量的各种信息,比如变量的类型、类别
2、如果是结构体,通过反射还可以获取结构体本身的信息,比如结构体的字段、结构体的方法、结构体的tag。
3、通过反射,可以修改变量的值,可以调用关联的方法。
Go 语言中的变量是分为两部分的:
• 类型信息:预先定义好的元信息。
• 值信息:程序运行过程中可动态变化的。
在GoLang的反射机制中,任何接口值都由是一个具体类型和具体类型的值两部分组成的。在GoLang中,反射的相关功能由内置的reflect包提供,任意接口值在反射中都可以理解为由reflect.Type和reflect.Value两部分组成,并且reflect包提供了reflect.TypeOf和reflect.ValueOf两个重要函数来获取任意对象的Value和Type。

1.1、reflect.TypeOf()获取任意值的类型对象

1、使用reflect.TypeOf可以获取函数类型对象。

package mainimport ("fmt""reflect"
)type myInt inttype Person struct {Name stringAge  int
}// 通过反射获取任意变量的类型
func reflectFn(x interface{}) {v := reflect.TypeOf(x)fmt.Println(v)
}func main() {reflectFn(10)var a = 10reflectFn(3.1415)reflectFn(true)reflectFn("你好golang")reflectFn([]int{1, 2, 3, 4, 5})reflectFn(&a)p := Person{Name: "张三",Age:  18,}reflectFn(p)var x myInt = 10reflectFn(x)
}

在这里插入图片描述

2、通过reflect.TypeOf获取返回的类型对象后,该对象里面还有两个方法Name和Kind。Name用来获取类型名称,Kind用来获取类型种类。

package mainimport ("fmt""reflect"
)type myInt inttype Person struct {Name stringAge  int
}func reflectFn(x interface{}) {v := reflect.TypeOf(x)fmt.Printf("类型: %v, 类型名称: %v, 类型种类: %v\n", v, v.Name(), v.Kind())
}func main() {var a = 10reflectFn(10)reflectFn(3.1415)reflectFn(true)reflectFn("你好golang")reflectFn([]int{1, 2, 3, 4, 5})reflectFn(&a)p := Person{Name: "张三",Age:  18,}reflectFn(p)var x myInt = 10reflectFn(x)
}

在这里插入图片描述

Go语言的反射中像数组、切片、Map、指针等类型的变量,它们的.Name()都是返回空。种类(Kind)就是指底层的类型。


1.2、reflect.ValueOf()

reflect.ValueOf()返回的是 reflect.Value 类型,其中包含了原始值的值信息。reflect.Value 与原始值之间可以互相转换。
在这里插入图片描述

1、例如实现接受任意值的接口,提取出原始值进行运算操作。

package mainimport ("fmt""reflect"
)func reflectFn(x interface{}) {v := reflect.ValueOf(x)num := v.Int() + 10fmt.Println(num)
}func main() {reflectFn(10)
}

在这里插入图片描述
在上面的代码中,我们先获取reflec.Value对象,然后通过该对象获取原始值进行运算操作。

2、但是上面这种情况是在我们知道类型的情况下,调用对应的获取原始值方法, 如果有多种类型,我们就需要进行判断。我们可以使用reflec.Value对象提供的kind函数获取种类,然后根据种类进行判断再调用对应的获取原始值方法。

package mainimport ("fmt""reflect"
)func reflectFn(x interface{}) {v := reflect.ValueOf(x)kind := v.Kind()switch kind {case reflect.Int:fmt.Printf("int类型的原始值: %v\n", v.Int())case reflect.Bool:fmt.Printf("bool类型的原始值: %v\n", v.Bool())case reflect.Float64:fmt.Printf("float64类型的原始值: %v\n", v.Float())case reflect.String:fmt.Printf("string类型的原始值: %v\n", v.String())default:fmt.Println("还没有判断这个类型...")}
}func main() {reflectFn(10)reflectFn(true)reflectFn(3.1415)reflectFn("你好golang")
}

在这里插入图片描述

3、在反射中修改变量的值。
想要在函数中通过反射修改变量的值, 需要注意函数参数传递的是值拷贝, 必须传递变量地址才能修改变量值。而反射中使用专有的 Elem()方法来获取指针对应的值。

package mainimport ("fmt""reflect"
)func reflectFn(x interface{}) {v := reflect.ValueOf(x)fmt.Println(v, v.Kind(), v.Elem(), v.Elem().Kind())
}func main() {var x = 10reflectFn(&x)
}

在这里插入图片描述
由于我们传入的是一个指针,所以获取值对象打印输出就是一个地址,通过kind获取类型是ptr,我们可以通过Elem函数来获取该指针指向的值,而不能通过解引用的方式来直接获取。要修改对应的值就先使用.Elem获取对象,然后再调用SetXXX来修改。

package mainimport ("fmt""reflect"
)func reflectFn(x interface{}) {v := reflect.ValueOf(x)if v.Elem().Kind() == reflect.Int {v.Elem().SetInt(20)} else if v.Elem().Kind() == reflect.String {v.Elem().SetString("hello c++")}
}func main() {var x = 10var str = "hello golang"fmt.Println(x, str)reflectFn(&x)reflectFn(&str)fmt.Println(x, str)
}

在这里插入图片描述


1.3、结构体反射

任意值通过reflect.TypeOf()获得反射对象信息后,如果它的类型是结构体,可以通过反射值对象(reflect.Type)的NumField()和Field()方法获得结构体成员的详细信息。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

1、通过类型变量的Field方法获取结构体字段。

package mainimport ("fmt""reflect"
)type Student struct {Name  string `json:"name1" form:"uername"`Age   int    `json:"age"`Score int    `json:"score"`
}func (s Student) GetInfo() {fmt.Printf("姓名: %v, 年龄: %v, 成绩: %v\n", s.Name, s.Age, s.Score)
}func (s *Student) SetInfo(name string, age int, score int) {s.Name = names.Age = ages.Score = score
}func PrintStructField(s Student) {t := reflect.TypeOf(s)// v := reflect.ValueOf(s)if t.Kind() != reflect.Struct && t.Elem().Kind() != reflect.Struct {fmt.Println("传入的不是一个结构体类型...")return}// 1.通过类型变量的Field方法获取结构体字段field0 := t.Field(0)fmt.Printf("%#v\n", field0)
}func main() {stu := Student{Name:  "张三",Age:   18,Score: 99,}PrintStructField(stu)
}

返回的是一个reflect.StructField对象,我们打印出看看里面有什么内容。
在这里插入图片描述
我们可以通过该结构体对象的Name、Type、Tag方法来获取对应的信息:

field0 := t.Field(0)
fmt.Printf("%#v\n", field0)
fmt.Println("字段名称:", field0.Name)
fmt.Println("字段类型:", field0.Type)
fmt.Println("字段Tag:", field0.Tag.Get("json"))
fmt.Println("字段Tag:", field0.Tag.Get("form"))

在这里插入图片描述

2、通过类型变量的FieldByName方法可以获取结构体字段。

field1, _ := t.FieldByName("Age")
fmt.Println("字段名称:", field1.Name)
fmt.Println("字段类型:", field1.Type)
fmt.Println("字段Tag:", field1.Tag.Get("json"))

在这里插入图片描述

3、通过类型变量的NumField方法可以获取到该结构体里有几个字段。

var fieldCount = t.NumField()
fmt.Println("该结构体字段数量:", fieldCount)

4、通过值变量获取结构体里面对应的值。

v := reflect.ValueOf(s)
fmt.Printf("Name的值: %v, Age的值: %v\n", v.Field(0), v.FieldByName("Age"))

5、通过类型变量里面的Method方法获取结构体中的方法。

func PrintStructFn(x interface{}) {t := reflect.TypeOf(x)if t.Kind() != reflect.Struct && t.Elem().Kind() != reflect.Struct {fmt.Println("传入的参数不是一个结构体...")return}method0 := t.Method(0)fmt.Println("方法名称:", method0.Name)fmt.Println("方法类型:", method0.Type)
}

在这里插入图片描述
这里传入0获取方法并不是按照方法的定义顺序来获取的,而是通过字典序来获取的。

6、通过类型变量里面的MethodByName获取方法。

method1, _ := t.MethodByName("GetInfo")
fmt.Println("方法名称:", method1.Name)
fmt.Println("方法类型:", method1.Type)

也可以通过NumMethod获取该结构体中有多少个方法。

7、通过值变量来执行方法。

v := reflect.ValueOf(x)
v.MethodByName("GetInfo").Call(nil)

上面调用GetInfo方法不需要传参,Call里面填写nil即可,如果需要传参需要定义一个reflect.Value切片传入,如下:

fmt.Println(x)
var params []reflect.Value
params = append(params, reflect.ValueOf("李四"))
params = append(params, reflect.ValueOf(22))
params = append(params, reflect.ValueOf(100))
v.MethodByName("SetInfo").Call(params)
fmt.Println(x)

在这里插入图片描述

8、反射修改结构体属性。

package mainimport ("fmt""reflect"
)type Student struct {Name  string `json:"name"`Age   int    `json:"age"`Score int    `json:"score"`
}func reflectChange(x interface{}) {t := reflect.TypeOf(x)v := reflect.ValueOf(x)if t.Kind() != reflect.Ptr {fmt.Println("传入的不是指针类型...")}if t.Elem().Kind() != reflect.Struct {fmt.Println("传入的不是结构体指针类型...")}name := v.Elem().FieldByName("Name")name.SetString("李四")age := v.Elem().FieldByName("Age")age.SetInt(22)
}func main() {stu := Student{Name:  "张三",Age:   18,Score: 100,}fmt.Println(stu)reflectChange(&stu)fmt.Println(stu)
}

在这里插入图片描述


2、文件操作

2.1、os.Open()打开文件

打开文件使用os.Open函数,传入文件的地址,可以采用绝对地址也可以采用相对地址。记得调用Close函数关闭文件。

package mainimport ("fmt""os"
)func main() {file, err := os.Open("./main.go")defer file.Close()if err != nil {fmt.Println("err:", err)return}
}

这种打开方式默认是只读的。


2.2、方式一:使用Read()读取文件

在这里插入图片描述

调用Read函数需要传入一个byte切片类型用来存储数据。该函数有两个返回值,第一个返回值表示读取的字节数。

package mainimport ("fmt""io""os"
)func main() {file, err := os.Open("./main.go")defer file.Close()if err != nil {fmt.Println("err:", err)return}var str []bytetmp := make([]byte, 128)for {n, err := file.Read(tmp)if err == io.EOF {fmt.Println("读取完毕...")break}if err != nil {fmt.Println("err:", err)return}str = append(str, tmp[:n]...)}fmt.Println(string(str))
}

注意:
1、每次只能读取128个字节,所以我们不知道什么时候读取完毕,通过对err == io.EOF来判断是否读取完毕。
2、切片是饮用类型,我们在拼接两个切片的时候要指明tmp的区间,否则可能会把之前残留的数据也拼接到str中。


2.3、方式二:bufio读取文件

package mainimport ("bufio""fmt""io""os"
)func main() {file, err := os.Open("./main.go")defer file.Close()if err != nil {fmt.Println(err)return}var fileStr stringreader := bufio.NewReader(file)for {str, err := reader.ReadString('\n') // 表示一次读取一行if err == io.EOF {fileStr += strbreak}if err != nil {fmt.Println(err)return}fileStr += str}fmt.Println(fileStr)
}

2.4、方式三:os.ReadFile读取

package mainimport ("fmt""os"
)func main() {byteStr, err := os.ReadFile("./main.go")if err != nil {fmt.Println(err)return}fmt.Println(string(byteStr))
}

2.5、写入文件

写入文件就不能使用os.Open()打开了,这样是只读的,需要使用os.OpenFile()函数。

func OpenFile(name string, flag int, perm FileMode) (*File, error) {
...
}

name:要打开的文件名。flag:打开文件的模式。模式有以下几种:
在这里插入图片描述
perm表示文件的权限,如果文件不存在我们创建文件的权限,传入0666即可。

下面演示三种写入文件的方式:
1、Write和WriteString写入。

package mainimport ("fmt""os"
)func main() {file, err := os.OpenFile("./file.txt", os.O_CREATE|os.O_APPEND|os.O_RDWR, 0666)defer file.Close()if err != nil {fmt.Println(err)return}for i := 0; i < 10; i++ {file.WriteString(fmt.Sprintf("我是一行字符串-%d\n", i))}var str = "哈哈哈哈哈"file.Write([]byte(str))
}

2、bufio.NewWriter配合Flush写入。

package mainimport ("bufio""fmt""os"
)func main() {file, err := os.OpenFile("./file.txt", os.O_CREATE|os.O_APPEND|os.O_RDWR, 0666)defer file.Close()if err != nil {fmt.Println(err)}writer := bufio.NewWriter(file)for i := 1; i <= 10; i++ {writer.WriteString(fmt.Sprintf("我是一行字符串-%d\n", i))}writer.Flush()
}

这里写入的是缓存中,我们还需要调用Flush刷新才行。

3、os.WriteFile写入。

package mainimport ("fmt""os"
)func main() {str := "hello world"err := os.WriteFile("./file.txt", []byte(str), 0666)if err != nil {fmt.Println(err)}
}

注意,这种写入的方式每次都会清空文件内容,所以如果要追加写入还是得采用前两种方式。


2.6、复制文件

实现方式一,通过os.ReadFile从文件中读取所有内容,再通过os.WriteFile写入到另一个文件中。

package mainimport ("fmt""os"
)func copy(srcFileName string, dstFileName string) error {byteStr, err := os.ReadFile(srcFileName)if err != nil {return err}err = os.WriteFile(dstFileName, byteStr, 0666)if err != nil {return err}return nil
}func main() {src := "./file1.txt"dst := "./file2.txt"err := copy(src, dst)if err != nil {fmt.Println(err)return}fmt.Println("复制文件成功")
}

方式二:方法流的方式复制。

package mainimport ("fmt""io""os"
)func copy(srcFileName string, dstFileName string) error {src, err := os.Open(srcFileName)defer src.Close()if err != nil {return err}dst, err := os.OpenFile(dstFileName, os.O_CREATE|os.O_TRUNC|os.O_RDWR, 0666)defer dst.Close()if err != nil {return err}var byteStr = make([]byte, 128)for {n, err := src.Read(byteStr)if err == io.EOF {break}if err != nil {return err}if _, err := dst.Write(byteStr[:n]); err != nil {return err}}return nil
}func main() {src := "./file1.txt"dst := "./file2.txt"err := copy(src, dst)if err != nil {fmt.Println(err)}fmt.Println("复制文件完成...")
}

2.7、文件重命名

使用os.Rename函数对文件进行重命名。

package mainimport ("fmt""os"
)func main() {err := os.Rename("./file1.txt", "./file2.txt")if err != nil {fmt.Println(err)return}fmt.Println("重命名成功...")
}

2.8、创建目录

使用os.Mkdir创建目录,使用os.MkdirAll创建多级目录。

package mainimport ("fmt""os"
)func main() {err := os.Mkdir("./abc", 0666)if err != nil {fmt.Println(err)return}fmt.Println("创建目录成功...")err = os.MkdirAll("./d1/d2/d3", 0666)if err != nil {fmt.Println(err)return}fmt.Println("创建多级目录成功...")
}

2.9、删除目录和文件

使用os.Remove删除目录或文件,使用os.RemoveAll删除多个文件或目录。

package mainimport ("fmt""os"
)func main() {err := os.Remove("./file1.txt")if err != nil {fmt.Println(err)return}err = os.Remove("./d1")if err != nil {fmt.Println(err)return}err = os.RemoveAll("./d2")if err != nil {fmt.Println(err)return}fmt.Println("删除成功...")
}

相关文章:

Golang——9、反射和文件操作

反射和文件操作 1、反射1.1、reflect.TypeOf()获取任意值的类型对象1.2、reflect.ValueOf()1.3、结构体反射 2、文件操作2.1、os.Open()打开文件2.2、方式一&#xff1a;使用Read()读取文件2.3、方式二&#xff1a;bufio读取文件2.4、方式三&#xff1a;os.ReadFile读取2.5、写…...

从 GreenPlum 到镜舟数据库:杭银消费金融湖仓一体转型实践

作者&#xff1a;吴岐诗&#xff0c;杭银消费金融大数据应用开发工程师 本文整理自杭银消费金融大数据应用开发工程师在StarRocks Summit Asia 2024的分享 引言&#xff1a;融合数据湖与数仓的创新之路 在数字金融时代&#xff0c;数据已成为金融机构的核心竞争力。杭银消费金…...

比较数据迁移后MySQL数据库和OceanBase数据仓库中的表

设计一个MySQL数据库和OceanBase数据仓库的表数据比较的详细程序流程,两张表是相同的结构,都有整型主键id字段,需要每次从数据库分批取得2000条数据,用于比较,比较操作的同时可以再取2000条数据,等上一次比较完成之后,开始比较,直到比较完所有的数据。比较操作需要比较…...

R 语言科研绘图第 55 期 --- 网络图-聚类

在发表科研论文的过程中&#xff0c;科研绘图是必不可少的&#xff0c;一张好看的图形会是文章很大的加分项。 为了便于使用&#xff0c;本系列文章介绍的所有绘图都已收录到了 sciRplot 项目中&#xff0c;获取方式&#xff1a; R 语言科研绘图模板 --- sciRplothttps://mp.…...

在鸿蒙HarmonyOS 5中使用DevEco Studio实现企业微信功能

1. 开发环境准备 ​​安装DevEco Studio 3.1​​&#xff1a; 从华为开发者官网下载最新版DevEco Studio安装HarmonyOS 5.0 SDK ​​项目配置​​&#xff1a; // module.json5 {"module": {"requestPermissions": [{"name": "ohos.permis…...

LabVIEW双光子成像系统技术

双光子成像技术的核心特性 双光子成像通过双低能量光子协同激发机制&#xff0c;展现出显著的技术优势&#xff1a; 深层组织穿透能力&#xff1a;适用于活体组织深度成像 高分辨率观测性能&#xff1a;满足微观结构的精细研究需求 低光毒性特点&#xff1a;减少对样本的损伤…...

Caliper 负载(Workload)详细解析

Caliper 负载(Workload)详细解析 负载(Workload)是 Caliper 性能测试的核心部分,它定义了测试期间要执行的具体合约调用行为和交易模式。下面我将全面深入地讲解负载的各个方面。 一、负载模块基本结构 一个典型的负载模块(如 workload.js)包含以下基本结构: use strict;/…...

【 java 虚拟机知识 第一篇 】

目录 1.内存模型 1.1.JVM内存模型的介绍 1.2.堆和栈的区别 1.3.栈的存储细节 1.4.堆的部分 1.5.程序计数器的作用 1.6.方法区的内容 1.7.字符串池 1.8.引用类型 1.9.内存泄漏与内存溢出 1.10.会出现内存溢出的结构 1.内存模型 1.1.JVM内存模型的介绍 内存模型主要分…...

(一)单例模式

一、前言 单例模式属于六大创建型模式,即在软件设计过程中,主要关注创建对象的结果,并不关心创建对象的过程及细节。创建型设计模式将类对象的实例化过程进行抽象化接口设计,从而隐藏了类对象的实例是如何被创建的,封装了软件系统使用的具体对象类型。 六大创建型模式包括…...

day36-多路IO复用

一、基本概念 &#xff08;服务器多客户端模型&#xff09; 定义&#xff1a;单线程或单进程同时监测若干个文件描述符是否可以执行IO操作的能力 作用&#xff1a;应用程序通常需要处理来自多条事件流中的事件&#xff0c;比如我现在用的电脑&#xff0c;需要同时处理键盘鼠标…...

群晖NAS如何在虚拟机创建飞牛NAS

套件中心下载安装Virtual Machine Manager 创建虚拟机 配置虚拟机 飞牛官网下载 https://iso.liveupdate.fnnas.com/x86_64/trim/fnos-0.9.2-863.iso 群晖NAS如何在虚拟机创建飞牛NAS - 个人信息分享...

android13 app的触摸问题定位分析流程

一、知识点 一般来说,触摸问题都是app层面出问题,我们可以在ViewRootImpl.java添加log的方式定位;如果是touchableRegion的计算问题,就会相对比较麻烦了,需要通过adb shell dumpsys input > input.log指令,且通过打印堆栈的方式,逐步定位问题,并找到修改方案。 问题…...

MinIO Docker 部署:仅开放一个端口

MinIO Docker 部署:仅开放一个端口 在实际的服务器部署中,出于安全和管理的考虑,我们可能只能开放一个端口。MinIO 是一个高性能的对象存储服务,支持 Docker 部署,但默认情况下它需要两个端口:一个是 API 端口(用于存储和访问数据),另一个是控制台端口(用于管理界面…...

怎么让Comfyui导出的图像不包含工作流信息,

为了数据安全&#xff0c;让Comfyui导出的图像不包含工作流信息&#xff0c;导出的图像就不会拖到comfyui中加载出来工作流。 ComfyUI的目录下node.py 直接移除 pnginfo&#xff08;推荐&#xff09;​​ 在 save_images 方法中&#xff0c;​​删除或注释掉所有与 metadata …...

作为测试我们应该关注redis哪些方面

1、功能测试 数据结构操作&#xff1a;验证字符串、列表、哈希、集合和有序的基本操作是否正确 持久化&#xff1a;测试aof和aof持久化机制&#xff0c;确保数据在开启后正确恢复。 事务&#xff1a;检查事务的原子性和回滚机制。 发布订阅&#xff1a;确保消息正确传递。 2、性…...

Caliper 配置文件解析:fisco-bcos.json

config.yaml 文件 config.yaml 是 Caliper 的主配置文件,通常包含以下内容: test:name: fisco-bcos-test # 测试名称description: Performance test of FISCO-BCOS # 测试描述workers:type: local # 工作进程类型number: 5 # 工作进程数量monitor:type: - docker- pro…...

第7篇:中间件全链路监控与 SQL 性能分析实践

7.1 章节导读 在构建数据库中间件的过程中&#xff0c;可观测性 和 性能分析 是保障系统稳定性与可维护性的核心能力。 特别是在复杂分布式场景中&#xff0c;必须做到&#xff1a; &#x1f50d; 追踪每一条 SQL 的生命周期&#xff08;从入口到数据库执行&#xff09;&#…...

基于PHP的连锁酒店管理系统

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

解决:Android studio 编译后报错\app\src\main\cpp\CMakeLists.txt‘ to exist

现象&#xff1a; android studio报错&#xff1a; [CXX1409] D:\GitLab\xxxxx\app.cxx\Debug\3f3w4y1i\arm64-v8a\android_gradle_build.json : expected buildFiles file ‘D:\GitLab\xxxxx\app\src\main\cpp\CMakeLists.txt’ to exist 解决&#xff1a; 不要动CMakeLists.…...

Vite中定义@软链接

在webpack中可以直接通过符号表示src路径&#xff0c;但是vite中默认不可以。 如何实现&#xff1a; vite中提供了resolve.alias&#xff1a;通过别名在指向一个具体的路径 在vite.config.js中 import { join } from pathexport default defineConfig({plugins: [vue()],//…...

基于Java+VUE+MariaDB实现(Web)仿小米商城

仿小米商城 环境安装 nodejs maven JDK11 运行 mvn clean install -DskipTestscd adminmvn spring-boot:runcd ../webmvn spring-boot:runcd ../xiaomi-store-admin-vuenpm installnpm run servecd ../xiaomi-store-vuenpm installnpm run serve 注意&#xff1a;运行前…...

PostgreSQL——环境搭建

一、Linux # 安装 PostgreSQL 15 仓库 sudo dnf install -y https://download.postgresql.org/pub/repos/yum/reporpms/EL-$(rpm -E %{rhel})-x86_64/pgdg-redhat-repo-latest.noarch.rpm# 安装之前先确认是否已经存在PostgreSQL rpm -qa | grep postgres# 如果存在&#xff0…...

MacOS下Homebrew国内镜像加速指南(2025最新国内镜像加速)

macos brew国内镜像加速方法 brew install 加速formula.jws.json下载慢加速 &#x1f37a; 最新版brew安装慢到怀疑人生&#xff1f;别怕&#xff0c;教你轻松起飞&#xff01; 最近Homebrew更新至最新版&#xff0c;每次执行 brew 命令时都会自动从官方地址 https://formulae.…...

为什么要创建 Vue 实例

核心原因:Vue 需要一个「控制中心」来驱动整个应用 你可以把 Vue 实例想象成你应用的**「大脑」或「引擎」。它负责协调模板、数据、逻辑和行为,将它们变成一个活的、可交互的应用**。没有这个实例,你的代码只是一堆静态的 HTML、JavaScript 变量和函数,无法「活」起来。 …...

Qemu arm操作系统开发环境

使用qemu虚拟arm硬件比较合适。 步骤如下&#xff1a; 安装qemu apt install qemu-system安装aarch64-none-elf-gcc 需要手动下载&#xff0c;下载地址&#xff1a;https://developer.arm.com/-/media/Files/downloads/gnu/13.2.rel1/binrel/arm-gnu-toolchain-13.2.rel1-x…...

BLEU评分:机器翻译质量评估的黄金标准

BLEU评分&#xff1a;机器翻译质量评估的黄金标准 1. 引言 在自然语言处理(NLP)领域&#xff0c;衡量一个机器翻译模型的性能至关重要。BLEU (Bilingual Evaluation Understudy) 作为一种自动化评估指标&#xff0c;自2002年由IBM的Kishore Papineni等人提出以来&#xff0c;…...

【LeetCode】3309. 连接二进制表示可形成的最大数值(递归|回溯|位运算)

LeetCode 3309. 连接二进制表示可形成的最大数值&#xff08;中等&#xff09; 题目描述解题思路Java代码 题目描述 题目链接&#xff1a;LeetCode 3309. 连接二进制表示可形成的最大数值&#xff08;中等&#xff09; 给你一个长度为 3 的整数数组 nums。 现以某种顺序 连接…...

关于uniapp展示PDF的解决方案

在 UniApp 的 H5 环境中使用 pdf-vue3 组件可以实现完整的 PDF 预览功能。以下是详细实现步骤和注意事项&#xff1a; 一、安装依赖 安装 pdf-vue3 和 PDF.js 核心库&#xff1a; npm install pdf-vue3 pdfjs-dist二、基本使用示例 <template><view class"con…...

STM32---外部32.768K晶振(LSE)无法起振问题

晶振是否起振主要就检查两个1、晶振与MCU是否兼容&#xff1b;2、晶振的负载电容是否匹配 目录 一、判断晶振与MCU是否兼容 二、判断负载电容是否匹配 1. 晶振负载电容&#xff08;CL&#xff09;与匹配电容&#xff08;CL1、CL2&#xff09;的关系 2. 如何选择 CL1 和 CL…...

Python 实现 Web 静态服务器(HTTP 协议)

目录 一、在本地启动 HTTP 服务器1. Windows 下安装 node.js1&#xff09;下载安装包2&#xff09;配置环境变量3&#xff09;安装镜像4&#xff09;node.js 的常用命令 2. 安装 http-server 服务3. 使用 http-server 开启服务1&#xff09;使用 http-server2&#xff09;详解 …...