在Java中,有三个操作字符串的类:
* String: 操作不可修改的字符串
* StringBuffer: 操作可修改的字符串,线程安全
* StringBuilder: 操作可修改的字符串,从Java 1.5开始引入,线程不安全,但操作比StringBuffer快。
在开发ugame p7的时候发现我对StringBuffer的线程安全发生误解。
Java的StringBuffer的线程安全并不是说只要操作StringBuffer就是线程安全,
而是说对StringBuffer对象的插入和追加操作对于同一StringBuffer实例而言是原子的,
不允许对同一StringBuffer实例的其它插入和追加操作和这个操作交错执行。
也就是说,多个读出写入的原子操作组成的操作并不原子:
用户界面读取一个StringBuffer静态对象GlobalCall.outputBuffer
然后把它清空:
//用定时器优化日志输出 display.timerExec(TIMER_INTERVAL, new Runnable() { @Override public void run() { //虽然StringBuffer线程安全, //但在读取toString()和setLength(0)清空之间 //存在交错执行的append输入 //所以要锁住防止交错 synchronized(GlobalCall.outputBuffer) { if(GlobalCall.outputBuffer.length() > 0) { logTab.logOutput.append( GlobalCall.outputBuffer.toString()); GlobalCall.outputBuffer.setLength(0); } } display.timerExec(TIMER_INTERVAL, this); } });
另一方面,在后台线程对这个StringBuffer对象执行追加操作
synchronized(outputBuffer) { outputBuffer.append(getTimeString() + str + "\n"); }
如果不加同步锁就会有问题,原因是,在用户界面线程里,append和setLength(0)执行期间,
后台线程可能对这个线程执行append操作。
结果,在此之间执行的append字符串没有来得及显示到界面上,就被setLength(0)删除了。
相关推荐
13. **HashMap 和 Hashtable 的区别**:HashMap 允许空键值对,是非线程安全的,而Hashtable不允许空键值对,是线程安全的。 14. **final, finally, finalize 的区别**:final 关键字用来声明变量不可改变,方法不...
Java 平台提供了两个类:String 和 StringBuffer,它们可以储存和操作字符串,即包含多个字符的字符数据。String 类提供了数值不可改变字符串,而 StringBuffer 类提供的字符串进行修改。当你知道字符数据要改变的...
包括 String 和 StringBuffer 的区别、ArrayList、Vector、LinkedList 的存储性能和特性、HashMap 和 Hashtable 的区别、final、finally、finalize 的区别、switch 语句的使用、多线程的实现方法、Java 中的流类型、...
1.4.1 类(Class):Java世界中一类物体 14 1.4.2 方法(Method):物体的功能 15 1.4.3 main()方法:所有Java程序执行的起点 15 .1.5 名词解释 16 1.5.1 JDK和Java平台 16 1.5.2 Java编译器(Java Compiler)...
Collections是针对集合类的一个帮助类,他提供一系列静态方法实现对各种集合的搜索、排序、线程安全化等操作。 13、&和&&的区别。 &是位运算符,表示按位与运算,&&是逻辑运算符,表示逻辑与(and)。 14、...
1.4.1 类(Class):Java世界中一类物体 14 1.4.2 方法(Method):物体的功能 15 1.4.3 main()方法:所有Java程序执行的起点 15 .1.5 名词解释 16 1.5.1 JDK和Java平台 16 1.5.2 Java编译器(Java Compiler)...
这些模式通常源于语言特性、API使用不当或对编程规范的误解。本篇将详细探讨一些常见的Java Bug模式,并提供预防和修复策略。 1. **空指针异常**:在Java中,NullPointerException是开发者最常遇到的错误之一。它...
- **java.lang包**:Object类的基础方法,Math类的数学运算,String类的字符串操作,StringBuffer类的线程安全字符串构建。 - **java.util包**:集合框架,包括List、Set、Map接口及其实现类,如ArrayList、HashSet...
在Java编程语言中,关于Java对象作为参数传递时的行为,存在一种常见的误解。许多人认为对象是按引用传递,而实际上,Java总是按值传递,包括对象。这里的“值”指的是对象的引用,而不是对象本身。这与C++或C#等...
《Java开发手册(嵩山版)灵魂15问》中提到的禁止使用Apache Beanutils进行属性复制的原因主要是性能和安全性的考虑。Apache BeanUtils提供了便捷的属性拷贝功能,但在大规模或高性能应用中,其效率相对较低。相比其他...
- **类加载机制**:Java虚拟机采用双亲委派模型来加载类,确保了核心类库的稳定性和安全性。 - **类加载时机**:类在首次主动使用时被加载,例如通过反射调用、实例化、静态字段引用等方式触发。 - **初始化过程**:...
Collections是针对集合类的一个帮助类,他提供一系列静态方法实现对各种集合的搜索、排序、线程安全化等操作。 10、&和&&的区别。 &是位运算符,表示按位与运算,&&是逻辑运算符,表示逻辑与(and)。 11、...