我使用以下代码抓取网页。
CloseableHttpClient httpclient = HttpClients.createDefault();
HttpGet httpget = new HttpGet(url);
CloseableHttpResponse response = httpclient.execute(httpget);
HttpEntity entity = response.getEntity();
System.out.println(entity.getContentType());
//output: Content-Type: text/html; charset=ISO-8859-1
我发现字符“'”的字节值为-110,无法映射到iso-8859-1或utf-8中的有效字符。
我尝试手动打开页面并复制字符并保存为文本文件,然后我看到字节值实际为39. 我认为操作系统在角色通过剪贴板时进行了转换
我想要的只是将网页保存为原始本地磁盘。
我制作了一个简单的代码来将内容保存到磁盘。我直接读取字节和写入字节。当我用十六进制编辑器打开保存的文件时,我可以看到该字节的值是146(-110)。
InputStream in = entity.getContent();
FileOutputStream fos = new FileOutputStream(new File("D:/test.html"));
byte[] buffer = new byte[1024];
int len = 0;
while((len = in.read(buffer)) > 0) {
fos.write(buffer, 0, len);
buffer = new byte[1024];
}
in.close();
fos.close();
所以现在问题变成了如何从字节146(-110)重建字符。如果我有任何东西,我会继续尝试和更新。
答案 0 :(得分:1)
也许您可以提供一些代码如何将页面保存到磁盘?你检查了’
的值吗?
看起来字符’
的长度为3个字节,除非我的粘贴或复制失败。看看这个:
public static void main(String[] args) {
char c = '’';
System.out.println("character: " + c);
System.out.println("int: " + (int)c);
String s = new String("’");
// Java uses UTF-16 encoding, other encodings will give different values
byte[] bytes = s.getBytes();
System.out.println("bytes: " + Arrays.toString(bytes));
}
编辑:我发现以下建议的charset处理方法,试一试:
ContentType contentType = ContentType.getOrDefault(entity);
Charset charset = contentType.getCharset();
Reader reader = new InputStreamReader(entity.getContent(), charset);
来源:https://hc.apache.org/httpcomponents-client-ga/tutorial/html/fundamentals.html
答案 1 :(得分:1)
Java中的字节是带符号的类型,其值为-128到127.最高有效位用于指示符号。例如,0111 1111 == 127,以及1000 0000 == -128。
我在ANSI表中查找了你的字符('),发现它的值为146(当然大于127)。二进制表示为1001 0010,因此将其解释为有符号值将产生-110。
重现您所看到的内容:
String s = new String("’"); // ’ is ansi character 146
byte[] bytes = s.getBytes();
System.out.println( (int)bytes[0] ); // prints -110
将字节值转换为无符号表示:
char c = (char)(bytes[0] & 0xFF);
System.out.println( (int)c ); // prints 146