理解Java中的字符串类型
1.Java内置对字符串的支持;
所谓的内置支持,即不用像C语言通过char指针实现字符串类型,并且Java的字符串编码是符合Unicode编码标准,这也意味着不用像C++那样通过使用string和wstring类实现与C语言兼容和Unicode标准。Java内部通过String类实现对字符串类型的支持。
这意味着:我们可以直接对字符串常量调用和String对象同样的方法:
//可以再"abc"上直接调用String对象的所有方法
int length="abc".length();
以及
String abc=new String("abc");
int length=abc.length();
2.Java中的字符串值是constant(常量的)
这里的意思是字符串类型在创建完成之后,是不能改变其中的值的,从String的成员方法也可以看出没有能改变值的方法接口;并且像"abc",new String("def")中的”abc","def"存放于Java虚拟机中的常量池。
以下的代码中的"abc"存放于常量池中,因此变量a,ab指向的地址均为常量池中同一个"abc"。
- public class StringTest {
- public static void main(String[] args) {
- String a="abc";
- String ab="abc";
- String abc=new String("abc");
- System.out.println(ab==a);
- System.out.println(a==abc);
- }
- }
- /*程序输出:
- * true
- * false
- * */
那么动态生成的、可变的字符串又是如何实现的呢?Java中提供StringBuffer和StringBuilder类实现这一需求;Java中字符串连接可以使用“+”操作符; 如:"abc"+"def";这里的内部实现也可以使用StringBuilder类或者StringBuffer类实现;那么StringBuilder和StringBuffer内部又是如何实现呢?是通过字符数组存储字符串。以下是从JDK附带的源码中找到的片段,可以看出StringBuffer内部使用char数组对字符串进行存储,其中的AbstractStringBuilder是StringBuffer的父类:
3.字符串中的编码问题。
这里要理解两个问题:如何处理源文件中的字符串编码?编译成class文件或者是代码在Java虚拟机运行时字符串是采用什么编码的?
第一个问题的理解是:源代码中的字符串编码取决于你的IDE或者文本编辑器。如以下的代码是使用GBK编码格式下编辑,然后使用UTF-8和GBK解码打开
//GBK编码格式,使用GBK格式打开
//GBK编码格式,使用UTF-8格式打开,乱码;如果此时系统默认的编码格式不是GBK时,在编译时需要在javac加入"-encoding GBK"参数选项值;
那么如何处理这种源代码编码的问题呢?答案是在编译器javac的参数选项-encoding中指定,默认这一参数的值是跟系统默认的编码一致。Windows的默认编码一般为GBK (可以通过System.getProperty("file.encoding")获得该值);在系统默认编码为GBK,但是源代码使用UTF-8编码,此时应该使用 javac -encoding UTF-8 进行编译。
对 ”编译成class文件或者是代码在Java虚拟机运行时字符串是采用什么编码的?“ 这个问题的理解是:首先,Java中的String类型是采用UTF-16编码实现的,也就是不管在源码的编码如何,在Java虚拟机中的字符串都是使用UTF-16编码实现。这意味着只要编译器javac正确的理解了源码文件中字符串的编码,运行时或者class字节码文件中的字符串是独立于源码中的编码格式的。这里我们可以进一步对java中的char基本类型或者Character类进行理解解,这两者内部的编码和java的字符串类型一样,都是基于UTF-16编码实现的,也就是不论‘a','1'这样的字符还是汉字在Java中的长度都是16位。
并且在String类型中也有着通过指定定字符编码,对底层二进制表示和字符串之间进行转化,也就意味着我们可以正确地读取GBK编码、UTF-8编码或者其他编码的文本文件或者其他输入流将其转化为内存中正确的字符串。
如String类中有如下的方法:
public String(byte[] bytes, Charset charset);通过指定定字符集编码类型,和相应的byte数组(byte长度为8位)构造字符串;
public byte[] getBytes(Charset charset);指定字符集编码类型,将字符串转化为byte数组,即字符串的二进制表示。
还有需要注意String的另一个成员方法:
public byte[] getBytes();这个方法返回的byte数组,所根据的字符集编码是指平台默认的字符集编码,而不一定是UTF-16。
理解Java中的字符串类型的更多相关文章
- java中,字符串类型的时间数据怎样转换成date类型。
将字符串类型的时间转换成date类型可以使用SimpleDateFormat来转换,具体方法如下:1.定义一个字符串类型的时间:2.创建一个SimpleDateFormat对象并设置格式:3.最后使用 ...
- 深入理解java中的byte类型
作者 | 进击的石头--GO! 来源 | https://www.cnblogs.com/zl181015/p/9435035.html#4432849 Java也提供了一个byte数据类型,并且是基 ...
- Java中的字符串驻留
转自:http://www.cdtarena.com/javapx/201307/9088.html 最近在工作的时候,一句再正常不过的代码String a = “hello” + “world”;被 ...
- 深入学习Java中的字符串,代码点和代码单元
在Java字符串处理时,在使用length和charAt方法时,应该格外小心,因为length返回的是UTF-16编码表示下的代码单元数量,而非我们所认为的字符的个数,charAt方法返回的是指定位置 ...
- 第48篇 说说.Net与Java中的字符串
原文地址:http://blog.laofu.online/2017/08/18/String-In-dotnet-Java/ Java字符串碰到的问题 在写Java程序碰到一个问题,而正是这个问题引 ...
- 深入理解Java中的IO
深入理解Java中的IO 引言: 对程序语言的设计者来说,创建一个好的输入/输出(I/O)系统是一项艰难的任务 < Thinking in Java > 本文的目录视图如下: ...
- 详解Java中的字符串
字符串常量池详解 在深入学习字符串类之前, 我们先搞懂JVM是怎样处理新生字符串的. 当你知道字符串的初始化细节后, 再去写String s = "hello"或String s ...
- 理解Java中字符流与字节流的区别
1. 什么是流 Java中的流是对字节序列的抽象,我们可以想象有一个水管,只不过现在流动在水管中的不再是水,而是字节序列.和水流一样,Java中的流也具有一个“流动的方向”,通常可以从中读入一个字节序 ...
- 理解Java中的弱引用(Weak Reference)
本篇文章尝试从What.Why.How这三个角度来探索Java中的弱引用,理解Java中弱引用的定义.基本使用场景和使用方法.由于个人水平有限,叙述中难免存在不准确或是不清晰的地方,希望大家可以指出, ...
随机推荐
- oc学习之路----application.keyWindow.rootViewController与self.window.rootViewController与[self.window makeKeyAndVisible];小发现
刚才调试的时候除了一些小问题,有一段代码要重用 NSString *key = @"CFBundleVersion"; // 取出沙盒中存储的上次使用软件的版本号 NSUserDe ...
- mybatis的$存在安全问题,为什么又不得不用?
1.mybatis的官网关于$和#的字符串替换符号区别描述如下: http://www.mybatis.org/mybatis-3/zh/sqlmap-xml.html#Parameters 上面的意 ...
- MSSQLSERVER数据库- 判断全局临时表是否存在
写一下今天遇到的一个问题. 今天因为一些作用域的问题,我使用了全局临时表,然后我在存储过程里使用了这么一段语句,想判断全局临时表是否存在,如果不存在,则将他DROP掉. 可是这段语句没用. if ex ...
- 如何获取web中某个元素的id
1.在原始的web界面上,切换到开发者模式,一般都有快捷键,本机的快捷键为(Ctrl+shift+I) 2.在开发者模式界面的左上角有一个放大镜的工具,点击一下,再去界面中找相应的元素,之后就可以定位 ...
- DevExpress MessageBox 弹出框 底层类
效果图: 前台调用: //图一的前台调用 MessageBox.Show("测试", "标题", MessageBoxButtons.OK); //图二的前台调 ...
- NAS、DAS和SAN三种存储究竟是什么?
首先,NAS(Network Attached Storage,网络附加存储)全面改进了以前低效的DAS存储方式,它是采用独立于PC服务器,单独为网络数据存储而开发的一种文件服务器. NAS服务器中集 ...
- [IOS地图开发系类]2、位置解码CLGeocoder
接第一步的操作,获取到地址信息经纬度后,我们可以对其进行解码,解码采用的CLGeocoder这个类,使用方式如下: 1.在ViewControlelr.m文件中声明一个CLGeocoder的属性, ...
- PHP操作SQLITE
一直以来.我们操作SQLITE,都是基于PHP默认的SQLITE操作模块. 今天介绍一个能够操作SQLITE2,和SQLITE3的PHP类,此为我封装的. <? php abstract cla ...
- java基础之synchronized使用方法
首先.參考文章:http://www.cnblogs.com/devinzhang/archive/2011/12/14/2287675.html PS:參考文章非常长,但内容非常丰富,若是刚開始学习 ...
- 测试浏览器最多能包含Cookie的个数和Cookie中包含的最多内容
public class CookieTestServlet extends HttpServlet { public void doGet(HttpServletRequest request, H ...