JAVA基础----String类型的简单介绍

news2024/12/27 13:15:29

文章目录

  • 1. String类的重要性
  • 2. 常用方法
    • 2.1 字符串构造
    • 2.2 String对象的比较
    • 2.3 字符串查找
    • 2.4 转化
    • 2.5 字符串替换
    • 2.6 字符串拆分
    • 2.7 字符串截取
    • 2.8 其他操作方法
    • 2.9 字符串的不可变性
    • 2.10 字符串修改
    • 2.11 借助StringBuffer 和 StringBuilder 观察String进行修改的效率
  • 3. StringBuilder和StringBuffer
    • 3.1 StringBuilder的介绍
    • 3.2 String、StringBuffer、StringBuilder的区别

1. String类的重要性

C语言中已经涉及到字符串了,但是在C语言中要表示字符串只能使用字符数组或者字符指针,可以使用标准库提供的字符串系列函数完成大部分操作,但是这种将数据和操作数据方法分离开的方式不符合面相对象的思想,而字符串应用又非常广泛,因此Java语言专门提供了String类。

2. 常用方法

2.1 字符串构造

String类提供的构造方式非常多,常用的就以下三种:

 	 // 使用常量串构造
     String s1 = "hello bit";
     System.out.println(s1);
 
     // 直接newString对象
     String s2 = new String("hello bit");
     System.out.println(s1);
 
     // 使用字符数组进行构造
     char[] array = {'h','e','l','l','o','b','i','t'};
     String s3 = new String(array);
     System.out.println(s1);

【注意】

  1. String是引用类型,内部并不存储字符串本身,在String类的实现源码中,String类实例变量如下:
    在这里插入图片描述
public static void main(String[] args) {
    // s1和s2引用的是不同对象 s1和s3引用的是同一对象
    String s1 = new String("hello");
    String s2 = new String("world");
    String s3 = s1;
    
    System.out.println(s1.length());   // 获取字符串长度---输出5
    System.out.println(s1.isEmpty());  // 如果字符串长度为0,返回true,否则返回false
}

在这里插入图片描述
2. 在Java中“”引起来的也是String类型对象。

// 打印"hello"字符串(String对象)的长度
System.out.println("hello".length());

2.2 String对象的比较

字符串的比较是常见操作之一,比如:字符串排序。Java中总共提供了4中方式:

1. == 比较是否引用同一个对象

注意:对于内置类型 ==, 比较的是变量中的值;对于引用类型 == 比较的是引用中的地址。

   int a = 10;
   int b = 20;
   int c = 10;

   // 对于基本类型变量,==比较两个变量中存储的值是否相同
   System.out.println(a == b);    // false
   System.out.println(a == c);    // true

   // 对于引用类型变量,==比较两个引用变量引用的是否为同一个对象
   String s1 = new String("hello");
   String s2 = new String("hello");
   String s3 = new String("world");
   String s4 = s1;
   System.out.println(s1 == s2);   // false
   System.out.println(s2 == s3);   // false
   System.out.println(s1 == s4);   // true

2. boolean equals(Object anObject) 方法:按照字典序比较

字典序:字符大小的顺序

String类重写了父类Object中equals方法,Object中equals默认按照==比较,String重写equals方法后,按照如下规则进行比较,比如: s1.equals(s2)

public static void main(String[] args) {
   String s1 = new String("hello");
   String s2 = new String("hello");
   String s3 = new String("Hello");

   // s1、s2、s3引用的是三个不同对象,因此==比较结果全部为false
   System.out.println(s1 == s2);       // false
   System.out.println(s1 == s3);       // false

   // equals比较:String对象中的逐个字符
   // 虽然s1与s2引用的不是同一个对象,但是两个对象中放置的内容相同,因此输出true
   // s1与s3引用的不是同一个对象,而且两个对象中内容也不同,因此输出false
   System.out.println(s1.equals(s2));  // true
   System.out.println(s1.equals(s3));  // false }

3. int compareTo(String s) 方法: 按照字典序进行比较

与equals不同的是,equals返回的是boolean类型,而compareTo返回的是int类型。具体比较方式:
1. 先按照字典次序大小比较,如果出现不等的字符,直接返回这两个字符的大小差值
2. 如果前k个字符相等(k为两个字符长度最小值),返回值两个字符串长度差值

public static void main(String[] args) {
    String s1 = new String("abc");
    String s2 = new String("ac");
    String s3 = new String("abc");
    String s4 = new String("abcdef");
    System.out.println(s1.compareTo(s2));   // 不同输出字符差值-1
    System.out.println(s1.compareTo(s3));   // 相同输出 0
    System.out.println(s1.compareTo(s4));   // 前k个字符完全相同,输出长度差值 -3 } 

4. int compareToIgnoreCase(String str) 方法:与compareTo方式相同,但是忽略大小写比较

public static void main(String[] args) {
    String s1 = new String("abc");
    String s2 = new String("ac");
    String s3 = new String("ABc");
    String s4 = new String("abcdef");
    System.out.println(s1.compareToIgnoreCase(s2));   // 不同输出字符差值-1
    System.out.println(s1.compareToIgnoreCase(s3));   // 相同输出 0
    System.out.println(s1.compareToIgnoreCase(s4));   // 前k个字符完全相同,输出长度差值 -3 } >```

2.3 字符串查找

字符串查找也是字符串中非常常见的操作,String类提供的常用查找的方法:

方法功能
char charAt(int index)返回index位置上字符,如果index为负数或者越界,抛出IndexOutOfBoundsException异常
int indexOf(int ch)返回ch第一次出现的位置,没有返回-1
int indexOf(int ch, int fromIndex)从fromIndex位置开始找ch第一次出现的位置,没有返回-1
int indexOf(String str)返回str第一次出现的位置,没有返回-1
int indexOf(String str, int fromIndex)从fromIndex位置开始找str第一次出现的位置,没有返回-1
int lastIndexOf(int ch)从后往前找,返回ch第一次出现的位置,没有返回-1
int lastIndexOf(int ch, int fromIndex)从fromIndex位置开始找,从后往前找ch第一次出现的位置,没有返回-1
int lastIndexOf(String str)从后往前找,返回str第一次出现的位置,没有返回-1
int lastIndexOf(String str, int fromIndex)从fromIndex位置开始找,从后往前找str第一次出现的位置,没有返回-1
  String s = "aaabbbcccaaabbbccc";
    System.out.println(s.charAt(3));                             // 'b'
    System.out.println(s.indexOf('c'));                          // 6
    System.out.println(s.indexOf('c', 10));                      // 15
    System.out.println(s.indexOf("bbb"));                        // 3
    System.out.println(s.indexOf("bbb", 10));                    // 12
    System.out.println(s.lastIndexOf('c'));                      // 17
    System.out.println(s.lastIndexOf('c', 10));                  // 8
    System.out.println(s.lastIndexOf("bbb"));                    // 12
    System.out.println(s.lastIndexOf("bbb", 10));                // 3

注意:上述方法都是实例方法。

2.4 转化

  1. 数值和字符串转化
public static void main(String[] args) {
    // 数字转字符串
    String s1 = String.valueOf(1234);
    String s2 = String.valueOf(12.34);
    String s3 = String.valueOf(true);
    String s4 = String.valueOf(new Student("Hanmeimei", 18));
    System.out.println(s1);
    System.out.println(s2);
    System.out.println(s3);    
    System.out.println(s4);    
    System.out.println("=================================");    

	// 字符串转数字    
	// 注意:Integer、Double等是Java中的包装类型   
	int data1 = Integer.parseInt("1234");    
	double data2 = Double.parseDouble("12.34");    
	System.out.println(data1);    
	System.out.println(data2); }
  1. 大小写转换
public static void main(String[] args) {    
	String s1 = "hello";    
	String s2 = "HELLO";    

	// 小写转大写    
	System.out.println(s1.toUpperCase());    

	// 大写转小写    
	System.out.println(s2.toLowerCase()); 
}
  1. 字符串转数组
public static void main(String[] args) {    
	String s = "hello";    

	// 字符串转数组    
	char[] ch = s.toCharArray();    
	for (int i = 0; i < ch.length; i++) {        
		System.out.print(ch[i]);   
	}    

	System.out.println();    

	// 数组转字符串    
	String s2 = new String(ch);    
	System.out.println(s2); 
}
  1. 格式化
public static void main(String[] args) {    
	String s = String.format("%d-%d-%d", 2019, 9,14);    
	System.out.println(s); 
}

2.5 字符串替换

使用一个指定的新的字符串替换掉已有的字符串数据,可用的方法如下:

方法功能
String replaceAll(String regex, String replacement)替换所有的指定内容
String replaceFirst(String regex, String replacement)替换首个内容

代码示例: 字符串的替换处理

String str = "helloworld" ; 
System.out.println(str.replaceAll("l", "_"));
System.out.println(str.replaceFirst("l", "_"));

运行结果:
he__owor_d
he_loworld

注意事项: 由于字符串是不可变对象, 替换不修改当前字符串, 而是产生一个新的字符串.

2.6 字符串拆分

可以将一个完整的字符串按照指定的分隔符划分为若干个子字符串。
可用方法如下:

方法功能
String[] split(String regex)将字符串全部拆分
String[] split(String regex, int limit)将字符串以指定的格式,拆分为limit组

代码示例: 实现字符串的拆分处理

String str = "hello world abc" ; 
String[] result = str.split(" ") ; // 按照空格拆分
for(String s: result) {
    System.out.println(s);
}


运行结果:
hello
world
abc

代码示例: 字符串的部分拆分

String str = "hello world hello bit" ; 
String[] result = str.split(" ",2) ; 
for(String s: result) {
    System.out.println(s);
}

运行结果:
hello
world abc

拆分是特别常用的操作. 一定要重点掌握. 另外有些特殊字符作为分割符可能无法正确切分, 需要加上转义.

代码示例: 拆分IP地址

String str = "192.168.1.1" ; 
String[] result = str.split("\\.") ; 
for(String s: result) {
    System.out.println(s);
}

String str3 = "192\\168\\1\\1";
String[] strings2 = str3.split("\\\\");//  \转义字符串
for (int i = 0; i < strings2.length; i++) {
    System.out.println(strings2[i]);
}

注意事项:

1. 字符".“,”|“,”*“,”+“都得加上转义字符,前面加上 “\\” .
2. 而如果是 “\\” ,那么就得写成 “\\\\” .
3. 如果一个字符串中有多个分隔符,可以用”|"作为连字符.

代码示例: 多次拆分

		String string = "name=zhangsanfeng&age=12";
        String[] ret = string.split("=|&");
        for (int i = 0; i < ret.length; i++) {
            System.out.println(ret[i]);
        }

        String[] ret2 = string.split("=");
        for (int i = 0; i < ret2.length; i++) {
            String s = ret2[i];
            String[] ret3 = s.split("&");
            for (int j = 0; j < ret3.length; j++) {
                System.out.println(ret3[j]);
            }
        }
}

运行结果:
zhangsanfeng
age
12
name
zhangsanfeng
age
12

2.7 字符串截取

从一个完整的字符串之中截取出部分内容。可用方法如下:

方法功能
String substring(int beginIndex)从指定索引截取到结尾
String substring(int beginIndex, int endIndex)截取部分内容

代码示例: 观察字符串截取

String str = "helloworld" ; 
System.out.println(str.substring(5));//w
System.out.println(str.substring(0, 5));//hello

注意事项:

1. 索引从0开始
2. 注意前闭后开区间的写法, substring(0, 5) 表示包含 0 号下标的字符, 不包含 5 号下标

2.8 其他操作方法

方法功能
String trim()去掉字符串中的左右空格,保留中间空格
String toUpperCase()字符串转大写
String toLowerCase()字符串转小写

代码示例: 观察trim()方法的使用

String str = "   hello world   " ; //只会去除两边的,不会去除中间的空格
System.out.println("["+str+"]");
System.out.println("["+str.trim()+"]");

运行结果:
[   hello world   ]
[hello world]

trim 会去掉字符串开头和结尾的空白字符(空格, 换行, 制表符等).

代码示例: 大小写转换

String str = "   hello%$$%@#$%world 哈哈哈 " ; 
System.out.println(str.toUpperCase());//只转换字母
System.out.println(str.toLowerCase());//只转换字母

运行结果:
  HELLO%$$%@#$%WORLD 哈哈哈 
  hello%$$%@#$%world 哈哈哈 

2.9 字符串的不可变性

String是一种不可变对象. 字符串中的内容是不可改变。字符串不可被修改,是因为:

  1. String类在设计时就是不可改变的,String类实现描述中已经说明了

以下来自JDK1.8中String类的部分实现:
在这里插入图片描述

字符串不可被修改,是因为value的值是被private限定修饰符所修饰的,无法获取value的内容,对value进行修改,所以字符串是不可变的

String类中的字符实际保存在内部维护的value字符数组中,该图中的两个final表示:

  • String类被final修饰,表明该类不能被继承
  • value被修饰被final修饰,表明value自身的值不能改变,即不能引用其它字符数组,但是其引用空间中的内容可以修改。

误区:
网上有些人说:字符串不可变是因为其内部保存字符的数组被final修饰了,因此不能改变。这种说法是错误的,不是因为String类自身,或者其内部value被final修饰而不能被修改。

final修饰类表明该类不想被继承,final修饰引用类型表明该引用变量不能引用其他对象,但是其引用对象中的内容是可以修改的

public static void main(String[] args) {
    final int array[] = {1,2,3,4,5};
    array[0] = 100;  //其引用对象中的内容是可以修改的
    System.out.println(Arrays.toString(array));
    // array = new int[]{4,5,6};   //该引用变量不能引用其他对象
    // 编译报错:Error:(19, 9) java: 无法为最终变量array分配值
}
  1. 所有涉及到可能修改字符串内容的操作都是创建一个新对象,改变的是新对象

比如 replace 方法:在这里插入图片描述

2.10 字符串修改

注意:尽量避免直接对String类型对象进行修改,因为String类是不能修改的,所有的修改都会创建新对象,效率非常低下。

public static void main(String[] args) {
    String s = "hello";
    s += " world";
    System.out.println(s);  // 输出:hello world
}

但是这种方式不推荐使用,因为其效率非常低,中间创建了好多临时对象。使用反编译查看:
在这里插入图片描述

在这里插入图片描述
上述代码等价于下面的代码:

public static void main(String[] args) {
        String s = "hello";
        StringBuilder temp = new StringBuilder();
        temp.append(s);
        temp.append(" world");
        s = temp.toString();
        System.out.println(s);
    }

我们发现在对String修改过程中,创建了额外的新的对象。

2.11 借助StringBuffer 和 StringBuilder 观察String进行修改的效率

public static void main(String[] args) {
        long start = System.currentTimeMillis();
        String s = "";
        for (int i = 0; i < 10000; ++i) {
            s += i;
        }
        long end = System.currentTimeMillis();
        System.out.println("String:"+ (end - start));

        start = System.currentTimeMillis();
        StringBuffer sbf = new StringBuffer("");
        for (int i = 0; i < 10000; ++i) {
            sbf.append(i);
        }
        end = System.currentTimeMillis();
        System.out.println("StringBuffer:"+ (end - start));

        start = System.currentTimeMillis();
        StringBuilder sbd = new StringBuilder();
        for (int i = 0; i < 10000; ++i) {
            sbd.append(i);
        }
        end = System.currentTimeMillis();
        System.out.println("StringBuilder:"+ (end - start));
    }
运行结果:
String293
StringBuffer1
StringBuilder1

对代码进行反编译:

String部分的代码:
在这里插入图片描述

StringBuilder和StringBuffer部分的代码:
在这里插入图片描述

综上所述,可以看到在对String类进行修改时,效率是非常慢的,因此:尽量避免对String的直接需要,如果要修改建议尽量使用StringBuffer或者StringBuilder。

3. StringBuilder和StringBuffer

3.1 StringBuilder的介绍

由于String的不可更改特性,为了方便字符串的修改,Java中又提供StringBuilder和StringBuffer类。
这两个类大部分功能是相同的,不同点是StringBuffer采用同步处理,属于线程安全操作;而StringBuilder未采用同步处理,属于线程不安全操作,这里介绍 StringBuilder常用的一些方法,其它需要用到了大家可参阅 StringBuilder在线文档

方法说明
StringBuff append(String str)在尾部追加,相当于String的+=,可以追加:boolean、char、char[]、double、float、int、long、Object、String、StringBuff的变量
char charAt(int index)获取index位置的字符
int length()获取字符串的长度
int capacity()获取底层保存字符串空间总的大小
void ensureCapacity(int mininmumCapacity)扩容
void setCharAt(int index, char ch)将index位置的字符设置为ch
int indexOf(String str)返回str第一次出现的位置
int indexOf(String str, int fromIndex)从fromIndex位置开始查找str第一次出现的位置
int lastIndexOf(String str)返回最后一次出现str的位置
int lastIndexOf(String str, int fromIndex)从fromIndex位置开始找str最后一次出现的位置
StringBuff insert(int offset, String str)在offset位置插入:八种基类类型 & String类型 & Object类型数据
StringBuffer deleteCharAt(int index)删除index位置字符
StringBuffer delete(int start, int end)删除[start, end)区间内的字符
StringBuffer replace(int start, int end, String str)将[start, end)位置的字符替换为str
String substring(int start)从start开始一直到末尾的字符以String的方式返回
String substring(int start,int end)将[start, end)范围内的字符以String的方式返回
StringBuffer reverse()反转字符串
String toString()将所有字符按照String的方式返回
public static void main(String[] args) {
        StringBuilder sb1 = new StringBuilder("hello");
        StringBuilder sb2 = sb1;
        
        // 追加:即尾插-->字符、字符串、整形数字
        sb1.append(' ');                  // hello
        sb1.append("world");              // hello world
        sb1.append(123);                  // hello world123
        System.out.println(sb1);          // hello world123
        System.out.println(sb1 == sb2);   // true
        System.out.println(sb1.charAt(0));   // 获取0号位上的字符 h
        System.out.println(sb1.length());    // 获取字符串的有效长度14
        System.out.println(sb1.capacity());  // 获取底层数组的总大小
        sb1.setCharAt(0, 'H');     // 设置任意位置的字符 Hello world123
        sb1.insert(0, "Hello world!!!");         // Hello world!!!Hello world123
        System.out.println(sb1);
        System.out.println(sb1.indexOf("Hello"));          // 获取Hello第一次出现的位置
        System.out.println(sb1.lastIndexOf("hello"));  // 获取hello最后一次出现的位置
        sb1.deleteCharAt(0);                               // 删除首字符
        sb1.delete(0,5);                                   // 删除[0, 5)范围内的字符
 
        String str = sb1.substring(0, 5);                  // 截取[0, 5)区间中的字符以String的方式返回
        System.out.println(str);
        sb1.reverse();                      // 字符串逆转
        str = sb1.toString();               // 将StringBuffer以String的方式返回
        System.out.println(str);
   }

从上述例子可以看出:String和StringBuilder最大的区别在于String的内容无法修改,而StringBuilder的内容可以修改。频繁修改字符串的情况考虑使用StringBuilder。

注意:String和StringBuilder类不能直接转换。如果要想互相转换,可以采用如下原则:

  • String变为StringBuilder: 利用StringBuilder的构造方法或append()方法
  • StringBuilder变为String: 调用toString()方法。

3.2 String、StringBuffer、StringBuilder的区别

  • String的内容不可修改,StringBuffer与StringBuilder的内容可以修改.
  • StringBuffer与StringBuilder大部分功能是相似的
  • StringBuffer采用同步处理,属于线程安全操作;而StringBuilder未采用同步处理,属于线程不安全操作
StringStringBufferStringBuilder
执行速度最差其次最高
线程安全线程安全线程安全线程不安全
使用场景少量字符串操作多线程环境下的大量操作单线程环境下的大量操作

【总结】

  • 不可变性:
    String 对象一旦被创建后,就不能再进行修改,只能通过创建新的 String对象来实现字符串内容的更新。这种设计可能会导致不必要的内存消耗和性能损失,尤其是在字符串修改频繁的情况下。
  • 线程安全性:
    StringBuilder 不是线程安全的类,这意味着在同一时间多个线程尝试修改同一个 StringBuilder
    时,可能发生数据不一致的情况。 StringBuffer 是一种线程安全的类,它通过使用 synchronized
    关键字和其他机制来确保在同一时刻只有一个线程能够访问字符串缓冲区,从而提供线程安全的环境。
  • 性能:
    StringBuilder 不需要进行加锁操作,因此在字符串拼接或修改操作较为繁重的情况下,性能通常优于 String 类型。 StringBuffer 虽然具有更好的线程安全性,但在执行这些操作时会有额外的开销,因此其性能可能会低于 StringBuilder

综上所述,如果你需要在单线程环境中进行大量的字符串拼接或修改,或者关心性能优化,那么选择StringBuilder 将更合适。而在多线程环境中,特别是需要确保线程安全的情况下,你应该选择 StringBuffer

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

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

相关文章

实时语音多实例实现设计方案(服务端)

1.端上接入协议 如何自行开发代码访问阿里语音服务_智能语音交互(ISI)-阿里云帮助中心 2.接口修改结果逻辑及端上调用步骤 阿里client server交互流程图&#xff1a; 阿里语音接收识别结果&#xff1a; begin_time time 含义 客户端循环发送语音数据&#xff0c;持续接收…

vue学习,使用provide/inject通信

提示&#xff1a;组件的provide&#xff0c;可以被其内所有层级的组件&#xff0c;通过inject引用 文章目录 前言一、通信组件二、效果三、参考文档总结 前言 需求&#xff1a;使用provide/inject通信 一、通信组件 1、AA.vue <template><div class"test"…

【开发实践】前端jQuery+gif图片实现载入界面

一、需求分析 载入界面&#xff08;Loading screen&#xff09;是指在计算机程序或电子游戏中&#xff0c;当用户启动应用程序或切换到新的场景时&#xff0c;显示在屏幕上的过渡界面。它的主要作用是向用户传达程序正在加载或准备就绪的信息&#xff0c;以及提供一种视觉上的反…

腾讯云2核2G4M云服务器值得买吗?

随着云计算技术的不断发展和普及&#xff0c;越来越多的企业和个人开始意识到云服务器的优势&#xff0c;并选择将其业务迁移至云端。作为国内领先的云计算服务提供商&#xff0c;腾讯云一直致力于为用户提供高品质的云服务器服务。其中&#xff0c;腾讯云2核2G4M云服务器备受关…

Docker 安装 MySQ

Docker 安装 MySQL MySQL 是世界上最受欢迎的开源数据库。凭借其可靠性、易用性和性能&#xff0c;MySQL 已成为 Web 应用程序的数据库优先选择。 1、查看可用的 MySQL 版本 访问 MySQL 镜像库地址&#xff1a;https://hub.docker.com/_/mysql?tabtags 。 可以通过 Sort b…

SpringBoot教程(十二) | SpringBoot集成JPA

SpringBoot教程(十二) | SpringBoot集成JPA 1. JPA简介 概念&#xff1a; JPA顾名思义就是Java Persistence API的意思&#xff0c;是JDK 5.0注解或XML描述对象&#xff0d;关系表的映射关系&#xff0c;并将运行期的实体对象持久化到数据库中。 优势&#xff1a; 标准化 …

Postman使用方法指南,最全面的教程

Postman使用教程 一、Postman介绍 ​ Postman是一个英语单词&#xff0c;名词&#xff0c;作名词时意为“邮递员&#xff1b;邮差”。 ​ Postman是一个接口测试工具,在做接口测试的时候,Postman相当于一个客户端,它可以模拟用户发起的各类HTTP请求,将请求数据发送至服务端,获…

【PS】PS设计图欣赏、学习、借鉴

【PS】PS设计图欣赏、学习、借鉴 bilibili萌新PS学习计划&#xff1a;PS教程全套零基础教学视频&#xff08;全套81节全新版本&#xff09;

Flink1.17 基础知识

Flink1.17 基础知识 来源&#xff1a;B站尚硅谷 目录 Flink1.17 基础知识Flink 概述Flink 是什么Flink特点Flink vs SparkStreamingFlink的应用场景Flink分层API Flink快速上手创建项目WordCount代码编写批处理流处理 Flink部署集群角色部署模式会话模式&#xff08;Session …

conda install命令无法安装pytorch

由于网络问题&#xff0c;直接采用conda install命令可能无法直接下载对应的cuda包。 方法一&#xff1a;采用pip命令替代 步骤1&#xff1a;切换pip的源为国内源&#xff1a; 若只是临时切换&#xff1a; pip install -i https://pypi.tuna.tsinghua.edu.cn/simple some-p…

分子动力学模拟—LAMMPS 模拟(固体和液体)数据后处理软件(六)

记录一下检索到一篇分子动力学模拟数据后处理的软件。 感谢论文的原作者&#xff01; 主要功能&#xff1a; Structure Analysis Ackland Jones Analysis CentroSymmetry Parameter Common Neighbor Analysis Common Neighbor Parameter Atomic Structure Entropy Stein…

9个在线图像压缩工具,可让您直接压缩 JPG、PNG 和 GIF 文件。

在这篇文章中&#xff0c;我们收集了九个出色的在线图像优化工具&#xff0c;可让您直接从网络浏览器压缩 JPG、PNG 和 GIF 文件。 除了分享有关每个工具的信息之外&#xff0c;我们还将分享测试 JPG 和 PNG 图像的真实测试数据&#xff0c;以便您了解每个工具可以节省的文件大…

C# 实现单线程异步互斥锁

文章目录 前言一、异步互斥锁的作用是什么&#xff1f;示例一、创建和销毁 二、如何实现&#xff1f;1、标识&#xff08;1&#xff09;标识是否锁住&#xff08;2&#xff09;加锁&#xff08;3&#xff09;解锁 2、异步通知&#xff08;1&#xff09;创建对象&#xff08;2&a…

SpringBoot基础:一步步创建SpringBoot工程

摘要 本文介绍了&#xff0c;从零开始创建SpringBoot工程&#xff0c;且在每一步给出分析和原因。创建maven – 转Springboot – 引入jdbc – 引入数据库操作框架&#xff0c;最后给出了不同场景指定不同配置文件的方案。 背景 为什么要使用SpringBoot工程&#xff1f; 使用Sp…

YOLOv8全网首发:DCNv4更快收敛、更高速度、更高性能,效果秒杀DCNv3、DCNv2等 ,助力检测

💡💡💡本文独家改进:DCNv4更快收敛、更高速度、更高性能,完美和YOLOv8结合,助力涨点 DCNv4优势:(1) 去除空间聚合中的softmax归一化,以增强其动态性和表达能力;(2) 优化存储器访问以最小化冗余操作以加速。这些改进显著加快了收敛速度,并大幅提高了处理速度,DCN…

X Winner受邀出席泰国政府加密峰会,上演未来独角兽的独角戏

​在近日&#xff0c;游戏化流动性&#xff08;Gamified Liquidity&#xff09;的基础设施 X WINNER &#xff0c;受邀出席了由泰国政府举办的“Blockchain to Government Conference ”大会。据了解&#xff0c;该会议是泰国政府布局 Web3 产业的一个重要标志&#xff0c;同时…

《WebKit 技术内幕》之四(2): 资源加载和网络栈

2.Chromium 多进程资源加载 2,1 多进程 资源的实际加载在各个WebKit移植中有不同的实现。Chromium采用的多进程的资源加载机制。 ResourceHandle 类之下的部分是不同移植对获取资源的不同实现&#xff0c;Chromium 中是 多进程资源加载 。主要是多个Renderer进程和Browser进程…

【汽车销售数据】2015~2023年各厂商各车型的探索 数据分析可视化

数据处理的思路&#xff1a; 1 各表使用情况&#xff1a; 汽车分厂商每月销售表&#xff0c;该表主要分析展示top10销量的厂商销量、占比变化情况&#xff08;柱形图、饼图&#xff09;&#xff1b;中国汽车分车型每月销售量表&#xff0c;该表主要分析展示top20销量的车型销…

五、基础篇 vue列表渲染

在v-for里使用对象用 v-for 把一个数组对应为一组元素 我们可以用 v-for 指令基于一个数组来渲染一个列表。v-for 指令需要使用 item in list形式的特殊语法&#xff0c;其中 list是源数据数组&#xff0c;而 item 则是被迭代的数组元素的别名。 <template><div clas…

Cuda与Torch配置(For 集群服务器)超详细步骤

每次配置模型环境&#xff0c;无论是在windows&#xff0c;linux&#xff0c;集群服务器上都会在这里卡一段&#xff0c;为了未来配置方便&#xff0c;记录下配置注意事项 配置cuda和torch主要有几个要点&#xff0c;分别是&#xff1a; 显卡与驱动&#xff08;NIVIADA drive…