Java 字节流与字符流(1)--对比

Java 的 IO 系统是比较庞杂的, 各种流特别多, 其中有一种就是字符流.

在本系列前面的一些文章中, 也曾涉及过字符流的话题, 不过没有详细展开讨论, 这次准备具体综合地谈一谈.

在层次方面的对比

你可能听过不少关于字节流与字符流对比的介绍, 不过严格地说, 我认为把"字节流"和"字符流"去对比这种说法不是特别妥当, 为什么呢?

首先, 这两种流实际上处在不同的层次, 字节流是基础, 而字符流是构建在其上的:

字节流 字符流 层级关系

对于不同层次上的事物, 我认为用"对比"这个词是不太恰当的.

继续阅读

非 BMP 字符判断及判断字符串中是否包含非 BMP 字符

判断一个字符是 BMP 字符还是非 BMP 字符(增补字符), 以及判断字符串中是否包含非 BMP 字符.

在 Java 中, 要判断一个字符是否为增补字符, 也即所谓的非 BMP 字符, 可以综合使用 String 类中的 codePointAtCharacter 类中的 isSupplementaryCodePoint 方法, 具体如下:

@Test
public void testSupplementaryCodePoint() throws Exception {
	// 一个非 BMP 字符
	String s = "𧿹";
	// 长度为 2
	assertThat(s.length()).isEqualTo(2);
	// 属于增补字符
	assertThat(Character.isSupplementaryCodePoint(s.codePointAt(0))).isTrue();
}

当然也可以简单地尝试将这个字符赋值给一个 char 变量, char 变量只能接受一个 BMP 字符, 如果是非 BMP 字符, 则编译不通过. 如果是一串的字符, 想知道其中是否存在非 BMP 字符, 则可以使用 codePointCount 方法:

@Test
public void testCodePointCount() throws Exception {
	String normalStr = "hi你";
	String strContainNoneBMP = "h𧿹你";
	
	// 两者的 length 不同
	assertThat(normalStr.length()).isEqualTo(3);
	assertThat(strContainNoneBMP.length()).isEqualTo(4);
	
	// 两者的码点数( code point count)却是相同的
	assertThat(normalStr.codePointCount(0, normalStr.length())).isEqualTo(3);
	assertThat(strContainNoneBMP.codePointCount(0, strContainNoneBMP.length())).isEqualTo(3);
}

继续阅读

Java 语言中一个字符占几个字节?

一个字符占几个字节? 很多人喜欢问这个问题, 遗憾的是他们没有意识到这其实是一个糟糕的问题, 因为它缺乏了必要的前提...

这是一个来自知乎上的问题, https://www.zhihu.com/question/27562173 , 提问者问:

Java 中理论说是一个字符(汉字 字母)占用两个字节. 但是在 UTF-8 的时候 new String("字").getBytes().length 返回的是 3 表示 3 个字节 小白求回答. .

严格地讲, 这个问题本身就是有问题的, 因为它缺少了前提, 在我的回答中我也强调了这一点, 回答具体如下:

首先, 你所谓的"字符"具体指什么呢? 如果你说的"字符"就是指 Java 中的 char, 那好, 那它就是 16 位, 2 字节.

如果你说的"字符"是指我们用眼睛看到的那些"抽象的字符", 那么, 谈论它占几个字节是没有意义的.

具体地讲, 脱离具体的编码谈某个字符占几个字节是没有意义的.

继续阅读

Java 大法好,GC 保平安——关于性能权衡(tradeoff)的一些思考

Java 之父 James Gosling 在一次接受采访谈到 C 语言时说:C 语言的一个大问题之一是“一切都会尖叫着停止”,"Everything comes to a screeching halt" is one of the big issues in C, because of the way that they do pointers……

语言的鄙视链是一直存在的,有人会以自己使用的语言更灵活,更底层,效率更高而自豪乃至鄙视其它一些语言的使用者,比如 C 语言的使用者可能看不上 Java 语言的使用者。Java 之父有一次谈到了 Java 与 C 语言的对比,他是怎么说的呢?

继续阅读