今天在工作中遇到一个问题,花了很久才解决,现在与大家分享一下。
问题的具体情况是这样的,我们的程序会从一个文本文件中读取数据。这个文件每行大概有1000个字符左右,但是我们需要的只是其中固定位置的10个字符左右的一段数据。具体的做法是每次都读取一行,然后使用subString来获取我们需要的值。之后将原来的大的字符串抛弃,将读取的小的字符串保存在一个Set中。
这段逻辑在进行JUnit测试的时候没有发现什么问题,但是在进行大数据量的性能测试的时候,确出现了占用大量内存的问题(远远超出了我们估计的内存使用量)。使用内存分析工具来查看,发现保存在Set中的字符串对象的大小明显异常。这是为什么呢?
我们使用Debug来检查这段代码,发现一个奇怪的问题。我们从一个1000字符的字符串中subString了一段10字符的字符串。但是查看subString的value属性的时候,value还是一个1000字符的字符数组,而不是我们想象中的10个字符的字符数组。这是为什么呢?
Code just do what you tell it to do. 代码只会做你让它做的事情。那么就让我们看看Java的源码吧。下面就是subString方法的源码:
- public String substring(int beginIndex, int endIndex) {
- if (beginIndex < 0) {
- throw new StringIndexOutOfBoundsException(beginIndex);
- }
- if (endIndex > count) {
- throw new StringIndexOutOfBoundsException(endIndex);
- }
- if (beginIndex > endIndex) {
- throw new StringIndexOutOfBoundsException(endIndex - beginIndex);
- }
- return ((beginIndex == 0) && (endIndex == count)) ? this :
- new String(offset + beginIndex, endIndex - beginIndex, value);
- }
复制代码
看看倒数第二行,这就是原因。Java源码并不是我们想象的那样将原来的字符串的value截取一段赋给新的字符串,而是直接将原来字符串的value赋给新字符串,然后通过制定offset和length的方法来创建新的字符串。原因找到了,修改起来就很简单,不必多说了。
Java这样做的好处是避免了内存的拷贝,对于String这样很基础的类来说,这样可以提高程序的效率。但是这个小小的“陷阱”,花费了我半天的时间。
分享到:
相关推荐
资源名称:substring截取字符串-Java中的方法-参考价值不大,需要的下.docx 内容概要: substring截取字符串,word格式,直接打开便可以学习使用,可以方便大家进行学习。虽说不可能全面,但也可以作为一个学习索引,...
oracle中 substring函数的使用
在操作sqlserver时候用到了substring函数 SUBSTRING ( expression, start, length ) 参数 expression 字符串、二进制字符串、文本、图像、列或包含列的表达式。请勿使用包含聚合函数的表达式。 start 整数或可以隐式...
substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 substring截取字符串 ...
主要介绍了Java中由substring方法引发的内存泄漏详解,涉及substring方法引发的内存泄漏简介,substring的作用和实现原理等相关内容,具有一定借鉴价值,需要的朋友可以参考下
java 如何使用substring()方法截取子串 java 如何使用substring()方法截取子串
实例方法引用,通过实例对象::实例方法,如 str::substring 构造方法引用,通过类名::new, 如 User::new 通过方法引用,可以将方法的引用赋值给一个变量,通过赋值给Function,说明方法引用也是一种函数式接口的...
实现一个按字节来截取字符串的方法,功能类似于string类的substring方法,String类是按字符截取 的,例如"中国abc".substring(1,3),将返回“国a”。这里 要求按字节截取,一个英文字符当一个字节,一个中文字符当两...
下面小编就为大家带来一篇浅谈Java的String中的subString()方法。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧
SQL 中的 substring 函数是用来抓出一个栏位资料中的其中一部分。这个函数的名称在不同的资料库中不完全一样: 参数: expression 字符串、二进制字符串、文本、图像、列或包含列的表达式。请勿使用包含聚合函数...
JavaScript 和.NET 中substr() 和 substring() 方法的区别
String可以使用substring方法进行截取字符串有两种,参数可输入一个或者两个: 单参数:public String substring(int beginIndex) ; 双参数:public String substring(int beginIndex, int endIndex) ;String 类...
C#中String类的几个方法(IndexOf、LastIndexOf、Substring)
SQL 中的 substring 函数是用来抓出一个栏位资料中的其中一部分。这个函数的名称在不同的资料库中不完全一样: MySQL: SUBSTR( ), SUBSTRING( ) Oracle: SUBSTR( ) SQL Server: SUBSTRING( ) SQL 中的 substring ...
NULL 博文链接:https://liuqing-2010-07.iteye.com/blog/1264845
主要介绍了3种javascript实现string的substring方法,需要的朋友可以参考下
substring用法简介
Arduino项目开发 Strings_StringSubstring_StringSubstring.pdf 学习资料 复习资料 教学资源
怎样使用Substring的应用以及对他的用法方法有更深的了解
substring方法返回基于给定参数的新的子字符串。 例子: <html> <head> <title>JavaScript String substring() Method</title> </head> <body> [removed] va