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

Java.lang中的String类和StringBuilder类介绍和常用方法

目录

Java.lang中的String类和StringBuilder类介绍和常用方法

String类介绍

String类的底层成员介绍

基本介绍

回顾String传址调用问题

String类对象的创建方式

String面试题

创建对象or不创建对象

创建了几个对象and共有几个对象

String常用方法

判断字符串是否相等方法

获取字符串内容方法

字符串转换

根据指定字符分割字符串

其他常用方法

StringBuilder类介绍

StringBuilder原理

StringBuilder的使用

StringBuilder对象创建方式

StringBuilder常用方法

StringBuilder与StringBuffer的区别


Java.lang中的String类和StringBuilder类介绍和常用方法

String类介绍

在Java中,String属于一种引用类型,表示字符串类型。实际上,在Java中,所有字符串字面量都是作为String类的对象实例化的,即使用双引号""包裹的都是String类的对象。

所以使用String s = "abc"表示的是创建了一个String类的对象内容为"abc",而s就是对象名,示意图如下:

根据官方文档对String类的描述,字符串都是常量,其值在创建后不可以被修改,所以在进行字符串拼接等对原始字符串内容进行的操作都是根据结果重新创建了一个新的字符串,例如下面的代码:

String s = "hello";
s += "world";

当对象s指向了"hello"时,此时堆中存在一个空间,其内容为"hello",而接下来想在原来的字符串中拼接"world"是做不到的,所以将拼接后的结果存入一个新空间返回给s,示意图如下:

因为String类的对象是不可变的,所以当出现内容相同的String对象,则不会二次创建String对象,而是共享已经创建的String对象,例如下面的代码:

public class Test {public static void main(String[] args) {String str1 = "abc";String str2 = "abc";System.out.println(str1 == str2);}
}输出结果:
true

String类的底层成员介绍

基本介绍

String类之所以底层的数据不可以修改,是因为底层使用了final修饰了字符串数组,在JDK8时,String底层成员是private final char value[];,而JDK9开始,String底层的成员变为private final byte[] value;。修改存储类型的目的还是为了节省空间

public class Call {public static void main(String[] args) {String arr1 = "字符串";change(arr1);// 方法内的修改不影响main函数arr1System.out.print(arr1);}public static void change(String arr1) {arr1 = "修改字符串";System.out.print(arr1);System.out.println();}
}

回顾String传址调用问题

根据上面的原理,再回顾前面在「传值调用和传址调用」中遇到的String对象通过形参传递

首先,对于Java中的引用数据类型来说,都是传址调用,这里的传址调用表示在方法中可以修改对应形参的内容,例如形参是数组类型时,可以在方法中修改数组中的内容,此时会影响实参

对于String类型,因为其也属于引用数据类型,所以传递给形参,在方法中理论上也可以改变其内容,但是实际上因为String类的属性被final修饰,导致无法在方法中修改其对应的内容,进而不会影响到实参字符串中的内容

而对于直接将对象引用传递给形参本质是实参对象引用的副本,不论是基本数据类型还是引用数据类型,将实参对象引用直接传递形参后,在方法中改变形参对应的对象引用指向都不会影响到方法外的形参对应的实参对应的对象引用指向

例如上面代码中,首先因为字符串不可变,所以"修改字符串"实际上是一块新的String类对象,而arr1 = "修改字符串";只是改变了arr1在方法change中的指向,但是因为arr1是直接传递给形参,所以方法中改变arr1的指向不会影响main函数中的arr1的指向

String类对象的创建方式

在官方文档中,提供了String类的许多构造方式,下面主要介绍常用的几种:

  1. 使用无参构造创建String类对象:String()
  2. 使用字符串创建String对象:String(String original)
  3. 使用char数组创建String对象:String(char[] value)
  4. 使用平台的默认字符集解码指定的 byte 数组,构造一个创建String对象:String(byte[] bytes)
对于第4种创建方式来说,平台表示当前Java代码所在的操作系统,默认字符集表示当前操作系统所使用的字符编码格式,Windows下默认是 GBK,解码表示根据 byte数组中的数值以及Java所在环境的编码格式进行与字符表对应的字符显示
需要注意,如果是在控制台使用 javac编译Java代码,则使用的编码根据操作系统决定,Windows下是 GBK,如果使用IDEA,则此时默认情况下是 UTF-8,因为IDEA启动编译时会自动加载一个启动参数( -Dfile.encoding=UTF-8),这个启动参数就是指定编码格式为 UTF-8,解码时就需要使用 UTF-8
如果想修改解码方式,可以在IDEA中进行下面的方式改变编码格式:
File->Settings->展开Editor->选择File Encodings->根据自己需要改变全局编码(Global Encoding)和项目编码(Project Encoding)

下面是上面四种构造方式的使用实例(第4种方式以GBK为例):

需要注意,在 GBK编码中,一个中文字符占用2个字节,所以在 byte数组中一个中文字符需要使用两个元素,而对于 UTF-8编码,一个中文字符占用3个字节,所以在 byte数组中一个中文字符需要使用三个元素
public class Test {public static void main(String[] args) {// 1. 使用无参构造创建String类对象:String()String str1 = new String();System.out.println(str1);// 2. 使用字符串创建String对象:String(String original)String str2 = new String("hello");System.out.println(str2);// 3. 使用char数组创建String对象:String(char[] value)char[] chars = {'a', 'b', 'c'};String str3 = new String(chars);System.out.println(str3);// 4. 使用平台的默认字符集解码指定的 byte 数组,构造一个创建String对象:String(byte[] bytes)// ASCII 码byte[] bytes = {97, 98, 99};String str4 = new String(bytes);System.out.println(str4);// GBK 编码byte[] bytes1 = {-60, -29, -70, -61};String str5 = new String(bytes1);System.out.println(str5);}
}输出结果:hello
abc
abc
你好

在实际使用String时,最常用的还是简写形式:

String 对象名 = "字符串"

两种特殊的构造String类对象的方式:

  1. 取出char数组中的部分字符构造String类对象:String(char[] value, int offset, int count)
  2. 取出byte数组中的部分字符构造String类对象:String(byte[] bytes, int offset, int length)
在上面的两种方式中,第一个参数代表对应数据类型的字符数组,第二个参数代表第一个包括的字符(即转换起点字符),第三个参数代表字符个数(从第二个参数代表的字符开始算起)

下面是实例代码:

public class Test {public static void main(String[] args) {// 1. 取出char数组中的部分字符构造String类对象:String(char[] value, int offset, int count)char[] chars1 = {'a', 'b', 'c', 'd', 'e'};String str6 = new String(chars1, 1, 3);System.out.println(str6);// 2. 取出byte数组中的部分字符构造String类对象:String(byte[] bytes, int offset, int length)byte[] bytes1 = {-60, -29, -70, -61};String str7 = new String(bytes1, 0, 2);System.out.println(str7);}
}输出结果:
bcd
你

String面试题

创建对象or不创建对象

思考下面代码的结果:

public class Demo04String {public static void main(String[] args) {String s1 = "abc";String s2 = "abc";String s3 = new String("abc");System.out.println(s1==s2); //trueSystem.out.println(s1==s3); //falseSystem.out.println(s2==s3); //false}
}

在上面的代码中,因为相同内容的字符串会共享,所以s1s2实际上指向的是同一块空间,但是对于s3来说,因为使用了new关键字,所以在堆内存创建了一块新空间,但是这块空间的内容因为与s1s2对应的字符串的内容相同,所以依旧是共享一块空间,但是s3指向的new开辟的新空间的地址,所以s3s1s2都不相同,示意图如下:

思考下面的代码结果:

public class Test02 {public static void main(String[] args) {String s1 = "hello";String s2 = "world";String s3 = "helloworld";String s4 = "hello"+"world";String s5 = s1+"world";String s6 = s1+s2;System.out.println(s3==s4); //trueSystem.out.println(s3==s5); //falseSystem.out.println(s3==s6); //false}
}

对于上面的代码来说,如果.class文件反编译成.java文件,就可以明白结果出现的原因,下面是反编译的结果:

可以看到,对于使用+两侧全是字符串常量直接拼接的,直接将拼接结果与其他字符串比对是否存在可共享的字符串,如果存在则直接使用;对于存在变量使用+进行拼接,则会调用StringBuilder()中的方法进行拼接,因为使用了new关键字,所以对象引用指向的空间地址并不是内容相同的字符串常量的地址

创建了几个对象and共有几个对象

思考下面的代码,回答:

  1. 对于第一行代码来说,创建了几个对象,共有几个对象
  2. 对于第二行代码来说,创建了几个对象,共有几个对象
String s1 = "abc"; // 1String s2 = new String("hello"); // 2

对于第一行代码来说,因为字符串在Java中属于String类的实例,即"abc"属于String类的对象,使s1指向了该对象,因此一共创建了1个对象,共有1个对象

对于第二行代码来说,首先"hello"会作为对象先创建,但是题目并没有说明在String s2 = new String("hello");之前是否已经创建了"hello"字符串对象,如果未创建,则包括new创建的对象在内一共创建了2个对象,共有2个对象;如果已经创建,根据字符串共享性,则包括new创建的对象在内一共创建了1个对象,共有2个对象

String常用方法

需要注意, String类的方法不仅是对象引用变量可以调用,字符串常量也可以调用,因为字符串常量也是 String类的对象

判断字符串是否相等方法

  1. boolean equals(String s)方法:因为String类重写了父类Object中的equals()方法,所以此处比较的字符串中的内容是否相等
  2. boolean equalsIgnoreCase(String s)方法:与equals()方法效果基本一致,只是忽略字母大小写

使用实例如下:

public class Test03 {public static void main(String[] args) {String s1 = "abc";String s2 = new String("abc");String s3 = "Abc";System.out.println(s1==s2);//比较地址值//boolean equals(String s)System.out.println(s1.equals(s2));//boolean equalsIgnoreCase(String s)System.out.println(s1.equalsIgnoreCase(s3));}
}
需要注意,上面的两个方法因为是对象调用,所以可能存在调用对象为空( null),为了避免出现空指针异常,也可以使用工具类 java.util.Objects中的 equals()方法进行比较,使用方式如下:
private static void method(String s1, String s2) {// 使用工具类Objects中的equals方法if (Objects.equals(s1, s2)) {System.out.println("相同字符串");} else{System.out.println("不相同字符串");}
}

下面是Objects工具类中的equals()方法源码:

public static boolean equals(Object a, Object b) {return (a == b) || (a != null && a.equals(b));
}

获取字符串内容方法

  1. 获取字符串长度:int length()
这里的获取长度是方法,不同于数组中的 length是数组的属性
  1. (拼接)拼接调用对象字符串和参数字符串:String concat(String s),返回一个新字符串的地址
  2. (字符下标)获取调用对象字符串中参数对应下标的字符:char charAt(int index)
  3. (查找字符)获取参数字符第一次在调用对象字符串中出现的位置:int indexOf(String s)
  4. (截取字符串)在调用对象字符串获取从参数位置开始(包括参数位置)之后的字符串,一直到最后一个字符:String subString(int beginIndex),返回一个新字符串
  5. (截取字符串)在调用对象字符串获取从参数位置开始(包括参数位置)之后的字符串,一直到第二个参数的位置对应的字符前一个字符(含第一个参数对应的字符,不含第二个参数对应的字符):String subString(int beginIndex,int endIndex),返回一个新字符串

基本使用实例如下:

public class Test03 {public static void main(String[] args) {String s1 = "abcdefg";//int length()System.out.println(s1.length());//String concat(String s)System.out.println(s1.concat("haha"));//char charAt(int index)System.out.println(s1.charAt(0));//int indexOf(String s)System.out.println(s1.indexOf("a"));//String subString(int beginIndex)System.out.println(s1.substring(3));//String subString(int beginIndex,int endIndex)System.out.println(s1.substring(1, 6));}
}输出结果:
7
abcdefghaha
a
0
defg
bcdef

使用上面的方法遍历字符串:

public class Test03 {public static void main(String[] args) {String s = "abcdefg";for (int i = 0; i < s.length(); i++) {System.out.println(s.charAt(i));}}
}

字符串转换

  1. 将字符串转换成char数组:char[] toCharArray()
  2. 将字符串转换成byte数组:byte[] getBytes()
  3. 替换字符串中的字符:String replace(CharSequence c1,CharSequence c2)
  4. 按照指定的编码将字符串转成byte数组:byte[] getBytes(String charsetName),注意本方法会抛出异常
第三种方法中的 CharSequenceString类实现的接口,所以根据多态(向上转型),可以直接传递 String类对象

基本使用如下:

public class Test04 {public static void main(String[] args) throws UnsupportedEncodingException {String s = "abcdefg";//1.char[] toCharArray()char[] chars = s.toCharArray();for (int i = 0; i < chars.length; i++) {System.out.print(chars[i] + " ");}System.out.println();//2.byte[] getBytes()byte[] bytes = s.getBytes();for (int i = 0; i < bytes.length; i++) {System.out.print(bytes[i] + " ");}System.out.println();//3.String replace(CharSequence c1,CharSequence c2)System.out.println(s.replace("a","z"));//4.byte[] getBytes(String charsetName)byte[] bytes1 = "你好".getBytes("GBK");for (int i = 0; i < bytes1.length; i++) {System.out.print(bytes1[i] + " ");}}
}输出结果:
a b c d e f g 
97 98 99 100 101 102 103 
zbcdefg
-60 -29 -70 -61 

根据指定字符分割字符串

使用方法:String[] split(String regex)

注意,方法的参数是正则表达式,如果想使用 .进行分割,需要对 .进行转义: \\.

使用实例如下:

public class Test05 {public static void main(String[] args) {String s = "abc,txt";String[] split = s.split(",");for (int i = 0; i < split.length; i++) {System.out.println(split[i]);}String s2 = "haha.hehe";String[] split1 = s2.split("\\.");for (int i = 0; i < split1.length; i++) {System.out.println(split1[i]);}}
}输出结果:
abc
txt
haha
hehe

其他常用方法

  1. 调用对象字符串是否包含参数中的字符串:boolean contains(String s)
  2. 调用对象字符串是否以参数字符串结尾:boolean endsWith(String s)
  3. 调用对象字符串是否以参数字符串开头:boolean startsWith(String s)
  4. 调用字符串中的大写字母转小写(本身为小写的不改变):String toLowerCase()
  5. 调用字符串中的小写字母转大写(本身为大写的不改变):String toUpperCase()
  6. 去掉字符串首尾空格(不会去除字符串内容中的空格):String trim()

基本使用如下:

public class Test06 {public static void main(String[] args) {String s = "abcdefg";//1.boolean contains(String s)System.out.println(s.contains("a"));//2.boolean endsWith(String s)System.out.println(s.endsWith("g"));//3.boolean startsWith(String s)System.out.println(s.startsWith("a"));//4.String toLowerCase()-> 将字母转成小写System.out.println("ADbcda".toLowerCase());//5.String toUpperCase() -> 将字母转成大写System.out.println("dafadRWERW".toUpperCase());//6.String trim()System.out.println(" hadfhad hdsfha  sfhdsh ".trim());// 拓展:使用替换字符串内容中的空格System.out.println("hadfhad hdsfha  sfhdsh".replace(" ",""));}
}输出结果:
true
true
true
adbcda
DAFADRWERW
hadfhad hdsfha  sfhdsh
hadfhadhdsfhasfhds

StringBuilder类介绍

String不同的是,StringBuilder是一个可变的字符序列,并且该类提供了一个与StringBuffer兼容的一套API,但是不保证同步,导致线程不安全,但是效率高,一般用于字符串拼接

之所以使用StringBuilder类进行拼接而不是String拼接是因为StringBuilder类的字符串可以改变,所以拼接可以在原字符串上拼接,但是String必须创建一个新对象,如果拼接次数太多,String就会影响整体效率

StringBuilder原理

StringBuilder类底层自带一个缓冲区(没有被final修饰的byte数组)拼接字符串之后都会在此缓冲区中保存,在拼接的过程中,不会随意产生新对象,节省内存,其特点是:

  1. 底层自带缓冲区,此缓冲区是没有被final修饰的byte数组,默认长度为16
  2. 如果字符串超出了已有的数组长度,数组会自动扩容,默认扩容大小是原来数组长度的2倍+2,但是如果扩容后的长度依旧不够,则会根据字符串的长度确定数组长度

StringBuilder的使用

StringBuilder对象创建方式

  1. 无参构造方法:StringBuilder()
  2. 使用String构造StringBuilder对象:StringBuilder(String str)

使用实例如下:

public class Test06 {public static void main(String[] args) {StringBuilder sb = new StringBuilder();System.out.println(sb);StringBuilder sb1 = new StringBuilder("abc");System.out.println(sb1);}
}

StringBuilder常用方法

  1. 字符串追加:StringBuilder append(任意类型数据),与String拼接不同,在原字符串基础上拼接,不会创建新对象
  2. 字符串翻转:StringBuilder reverse(),返回原字符串翻转后的结果,不会创建新对象
  3. StringBuilderStringString toString(),转换是为了便于后面使用String的方法

基本使用实例:

public class Test {public static void main(String[] args) {StringBuilder sb = new StringBuilder();StringBuilder sb1 = sb.append("abc");System.out.println(sb1);System.out.println(sb);System.out.println(sb==sb1);//链式调用sb.append("def").append("g").append("f");System.out.println(sb);sb.reverse();System.out.println(sb);String s = sb.toString();System.out.println(s);}
}输出结果:
abc
abc
true
abcdefgf
fgfedcba
fgfedcba

方法实用:

判断一个字符串是否是「回文字符串」:

public class Test01 {public static void main(String[] args) {String str = "abcba";StringBuilder sb = new StringBuilder(str);// 使用StringBuilder中的reverse方法反转字符串,反转完后转换为String使用其equals方法判断内容是否相同,如果反转与原字符串相等,则是回文串boolean result = sb.reverse().toString().equals(str);System.out.println(result);}
}

StringBuilderStringBuffer的区别

相同点:

用法一样,作用一样

不同点:

  1. StringBuilder:拼接效率比StringBufferString高,但是线程不安全
  2. StringBuffer:效率比较底,但是线程安全
  • 拼接效率:StringBuilder>StringBuffer>String

相关文章:

Java.lang中的String类和StringBuilder类介绍和常用方法

目录 Java.lang中的String类和StringBuilder类介绍和常用方法 String类介绍 String类的底层成员介绍 基本介绍 回顾String传址调用问题 String类对象的创建方式 String面试题 创建对象or不创建对象 创建了几个对象and共有几个对象 String常用方法 判断字符串是否相等方法 获取字…...

notepad++软件介绍(含安装包)

Notepad 是一款开源的文本编辑器&#xff0c;主要用于编程和代码编辑。它是一个功能强大的替代品&#xff0c;常常被用来替代 Windows 系统自带的记事本。 Notepad win系统免费下载地址 以下是 Notepad 的一些主要特点和功能&#xff1a; 多语言支持&#xff1a;Notepad 支持多…...

chapter13-常用类——(章节小结)——day17

498-常用类阶段梳理...

RTX AI PC 和工作站上部署多样化 AI 应用支持 Multi-LoRA

今天的大型语言模型&#xff08;LLMs&#xff09;在许多用例中都取得了前所未有的成果。然而&#xff0c;由于基础模型的通用性&#xff0c;应用程序开发者通常需要定制和调整这些模型&#xff0c;以便专门针对其用例开展工作。 完全微调需要大量数据和计算基础设施&#xff0…...

C++ STL-deque容器入门详解

1.1 deque容器基本概念 功能&#xff1a; 双端数组&#xff0c;可以对头端进行插入删除操作 deque与vector区别&#xff1a; vector对于头部的插入删除效率低&#xff0c;数据量越大&#xff0c;效率越低deque相对而言&#xff0c;对头部的插入删除速度回比vector快vector访…...

数据结构之折半查找

折半查找&#xff08;Binary Search&#xff09;&#xff0c;也称为二分查找&#xff0c;是一种在有序数组中查找特定元素的搜索算法。其工作原理是&#xff0c;通过不断将待查找的区间分成两半&#xff0c;并判断待查找的元素可能存在于哪一半&#xff0c;然后继续在存在可能性…...

linux高级学习12

24.9.9学习目录 一.条件变量 一.条件变量 通常条件变量和互斥锁同时使用&#xff1b; 条件变量是用来阻塞线程&#xff0c;其本身并不是锁&#xff0c;直到达到特定的要求&#xff1b; &#xff08;1&#xff09;条件变量初始化 #include <pthread.h> int pthread_con…...

leetcode:3174 清除数字 使用栈,时间复杂度O(n)

3174 清除数字 题目链接 题目描述 给你一个字符串 s 。 你的任务是重复以下操作删除 所有 数字字符&#xff1a; 删除 第一个数字字符 以及它左边 最近 的 非数字 字符。 请你返回删除所有数字字符以后剩下的字符串。 示例 1&#xff1a; 输入&#xff1a;s "abc…...

神经网络卷积操作

文章目录 一、nn.Conv2d二、卷积操作原理三、代码实现卷积操作 一、nn.Conv2d nn.Conv2d 是 PyTorch 中的一个类&#xff0c;它代表了一个二维卷积层&#xff0c;通常用于处理图像数据。在深度学习和计算机视觉中&#xff0c;卷积层是构建卷积神经网络&#xff08;CNN&#xf…...

专题二_滑动窗口_算法专题详细总结

目录 滑动窗口&#xff0c;引入&#xff1a; 滑动窗口&#xff0c;本质&#xff1a;就是同向双指针&#xff1b; 1.⻓度最⼩的⼦数组&#xff08;medium&#xff09; 1.解析&#xff1a;给我们一个数组nums&#xff0c;要我们找出最小子数组的和target&#xff0c;首先想到的…...

【机器学习-三-无监督学习】

无监督学习 什么是无监督学习分类聚类降维 有监督和无监督学习的区别 上一节介绍了监督学习&#xff0c;下面来介绍无监督学习&#xff0c;这也是最广泛应用的算法。 什么是无监督学习 上一节中&#xff0c;我们知道了监督学习是通过 对算法&#xff0c;**输入一对数据&#x…...

JAVA基础:Lambda表达式(上)

前言 Lambda表达式是jdk1.8的一个新特性&#xff0c;他属于一种语法堂主要作用是对匿名内部类语法简化 lambda基本应用 lambda表达式想要优化匿名内部类是有前提条件&#xff0c;首先必须是一个接口&#xff0c;而且要求接口中只能有1个抽象方法&#xff0c;称之为函数式接口…...

Vue使用fetch获取本地数据

&#xff08;1&#xff09;使用get test.json文件 { "list":[111,222,333] } <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initi…...

《酒饮真经》秘籍4,让你的酒场技巧更上一层楼!

在酒桌这一独特的舞台上&#xff0c;每个人都扮演着不同的角色&#xff0c;或攻或守&#xff0c;尽显智慧与风度。对于不擅长喝酒的人来说&#xff0c;如何在推杯换盏间既保护自己又不失礼节&#xff0c;是值得我们仔细研究的。下面是酱酒亮哥为您整理的一系列实用的酒桌攻防秘…...

回车符与快捷键记录

一.在Windows和Linux操作系统中&#xff0c;回车符&#xff08;或称为换行符&#xff09;的处理方式区别 1.Windows下的回车符 在Windows系统中&#xff0c;回车符通常是由两个字符组成的序列&#xff1a;回车符&#xff08;Carriage Return&#xff0c;简称CR&#xff0c;AS…...

计算机网络-VRRP工作原理

一、VRRP工作原理 前面我们大概了解了VRRP的一些基础概念&#xff0c;现在开始学习VRRP的技术原理。VRRP的选举及工作步骤&#xff1a; 确定网关地址 选举主备 主设备发送VRRP报文通知Backup设备 主设备响应终端ARP并维持在Master状态 终端正常发送报文到网关进行转发 因为我们…...

6.5椒盐噪声

在OpenCV中联合C给一张图片加上椒盐噪声&#xff08;Salt and Pepper Noise&#xff09;可以通过随机选择像素点并将其置为黑色&#xff08;0&#xff09;或白色&#xff08;255&#xff09;来实现。椒盐噪声是一种随机噪声&#xff0c;通常表现为图像中的孤立黑点&#xff08;…...

CSS样式的引用方式以及选择器使用

1. CSS 引用方式 CSS 可以通过三种方式引用到 HTML 文件中&#xff1a; 行内样式&#xff08;Inline Styles&#xff09;&#xff1a;直接在 HTML 元素中定义样式。内部样式表&#xff08;Internal CSS&#xff09;&#xff1a;在 HTML 文档的 <head> 部分使用 <sty…...

Python Flask_APScheduler定时任务的正确(最佳)使用

描述 APScheduler基于Quartz的一个Python定时任务框架&#xff0c;实现了Quartz的所有功能。最近使用Flask框架使用Flask_APScheduler来做定时任务&#xff0c;在使用过程当中也遇到很多问题&#xff0c;例如在定时任务调用的方法中需要用到flask的app.app_context()时&#…...

Linux命名管道

​ ​通信的前提是让不同的进程看到同一份资源&#xff0c;因为路径是具有唯一性的&#xff0c;所以我们可以使用路径文件名来唯一的让不同进程看到同一份资源&#xff0c;实现没有血缘关系的两个进程进行管道通信 1.指令级 mkfifio&#xff08;FILENAME,0666&#xff09; …...

Xinstall助力App全渠道统计,参数传递下载提升用户体验!

在移动互联网时代&#xff0c;App已成为我们日常生活中不可或缺的一部分。然而&#xff0c;对于App开发者来说&#xff0c;如何有效地推广和运营自己的应用&#xff0c;却是一个不小的挑战。尤其是在面对众多渠道、复杂的数据统计和用户需求多样化的情况下&#xff0c;如何精准…...

【时时三省】(C语言基础)指针进阶 例题4

山不在高&#xff0c;有仙则名。水不在深&#xff0c;有龙则灵。 ----CSDN 时时三省 strlen是求字符串长度 这个需要算上&#xff3c;0 第一个arr 是打印6 因为它加上&#xff3c;0是有六个元素 第二个arr0 数组名相当于首元素的地址 a的地址加0还是a的地址 所以这个地方还是…...

k8s的配置管理

一、配置管理分为两种&#xff1a; 1. 加密配置&#xff1a;用来保存密码和token密钥对以及其它敏感的k8s资源。 2.应用配置&#xff1a;我们需要定制化的给应用进行配置&#xff0c;我们需要把定制好的配置文件同步到pod当中的容器。 二、加密配置 1.secret三种类型&#xf…...

JAVA- 多线程

一&#xff0c;多线程的概念 1.并行与并发 并行&#xff1a;多个任务在同一时刻在cpu 上同时执行并发&#xff1a;多个任务在同一时刻在cpu 上交替执行 2.进程与线程 进程&#xff1a;就是操作系统中正在运行的一个应用程序。所以进程也就是“正在进行的程序”。&#xff0…...

【Qt】解决设置QPlainTextEdit控件的Tab为4个空格

前言 PyQt5 是一个用于创建跨平台桌面应用程序的 Python 绑定集合&#xff0c;它提供了对 Qt 应用程序框架的访问。用于开发具有图形用户界面&#xff08;GUI&#xff09;的应用程序&#xff0c;以及非GUI程序。PyQt5 使得 Python 开发者可以使用 Qt 的丰富功能来构建应用程序。…...

elementUI根据列表id进行列合并@莫成尘

本文章提供了elementUI根据列表id进行列合并的demo&#xff0c;效果如图&#xff08;可直接复制代码粘贴&#xff09; <template><div id"app"><el-table border :data"tableList" style"width: 100%" :span-method"objectS…...

基于人工智能的智能安防监控系统

目录 引言项目背景环境准备 硬件要求软件安装与配置系统设计 系统架构关键技术代码示例 数据采集与预处理模型训练与预测实时监控与检测应用场景结论 1. 引言 随着科技的发展&#xff0c;智能安防监控系统逐渐成为家庭、企业和公共场所保障安全的核心工具。通过人工智能和计…...

分享从零开始学习网络设备配置--任务6.3 使用基本ACL限制网络访问

任务描述 某公司构建了互联互通的办公网&#xff0c;为保护公司内网用户数据的安全&#xff0c;该公司实施内网安全防范措施。公司分为经理部、财务部和销售部&#xff0c;分属3个不同的网段&#xff0c;3个部门之间用路由器进行信息传递。为了安全起见&#xff0c;公司领导要求…...

数据结构——线性表(静态链表、循环链表以及双向链表)

1、静态链表 用数组描述的链表叫做静态链表&#xff0c;这种描述方法叫做游标实现法。 静态链表需要对数组的第一个和最后一个元素作为特殊元素处理&#xff0c;不存数据。 最后一个指向第一个有数据的下标地址&#xff0c;第一个游标指向第一个没有数据的下标地址。 我们对…...

vue3_对接腾讯_实时音视频

项目需要对接腾讯的实时音视频产品&#xff0c;我这里选择的是多人会议&#xff0c;选择其他实时音视频产品对接流程也一样&#xff0c;如何对接腾讯实时音视频的多人会议产品&#xff0c;从开通服务到对接完成&#xff0c;一 一讲解。 一、开通腾讯实时音视频 1.腾讯实时音视…...