Java 在抓取俄罗斯网站时出现垃圾角色

Java 在抓取俄罗斯网站时出现垃圾角色,java,linux,encoding,web-crawler,cyrillic,Java,Linux,Encoding,Web Crawler,Cyrillic,我试图在Linux中抓取一个俄语网站,但输出的似乎是垃圾字符。 该网站是用UTF-8编码的,在阅读时我将编码设置为UTF-8。然而,这似乎并不能解决问题。 我该怎么读呢 public class Crawl { @SuppressWarnings("unused") public static void main(String[] args) { URL my_url = new URL("http://www.fmsmoscow.ru/docs/migratio

我试图在Linux中抓取一个俄语网站,但输出的似乎是垃圾字符。 该网站是用UTF-8编码的,在阅读时我将编码设置为UTF-8。然而,这似乎并不能解决问题。 我该怎么读呢

public class Crawl {   
    @SuppressWarnings("unused")
    public static void main(String[] args) {

    URL my_url = new URL("http://www.fmsmoscow.ru/docs/migration_registration/registration.html");
    BufferedReader br = new BufferedReader(new InputStreamReader(my_url.openStream(),"UTF-8"));
    while (null != (strTemp = br.readLine())){
    System.out.println(strTemp);
        }
    }   
}
以上是相同的代码。 我将代码导出为jar并将其添加到Linux服务器中。
然后我执行它以在Linux控制台中获得输出。

通常,您也可以按原样存储内容二进制文件,然后查看哪里出错。比如说在一个程序员的编辑器中,比如JEdit或NotePad++可以切换编码。它可能会在本机Windows-1251的HTML注释中出现。也许剥离HTML注释会有所帮助

对于容错解码、错误报告,需要

: 请参阅关于REPLACE、REPORT的javadoc。如果你想要更多,方法是不同的。您需要读取输入,将字节放入ByteBuffer,然后

CoderResult result = decoder(byteBuffer, charBuffer, true /*EOF*/);

要从UTF-8中提取西里尔序列,可以检查UTF-8序列的有效性:

  • 0xxxxxxx
  • 110xxxxx 10xxxxxx
  • 1110xxxx 10xxxxxx 10xxxxxx
因此(未经测试):

void patchmixOfUf8andCP1251(字节[]字节,StringBuilder sb){
布尔值priorErrorUTF8=false;
对于(int i=0;i=0){
sb.附加码点((int)b);
PriorErrorUTF8=错误;
}否则{
int n=高位(b);//也按顺序为#字节
布尔值isUTF8=!优先级错误UTF8

&&1Cp1251
,即使该站点被认为是UTF-8编码的?3)请向其添加代码(以及您使用的任何语言的适当标记)。当它遇到俄文字符时出错,它可以完美地抓取页面的其余部分。添加了一个补丁功能(未经测试!)。这些功能可以在有限的范围内工作。
CoderResult result = decoder(byteBuffer, charBuffer, true /*EOF*/);
void patchMixOfUtf8AndCp1251(byte[] bytes, StringBuilder sb) {
    boolean priorWrongUtf8 = false;
    for (int i = 0; i < bytes.length; ++i) {
        byte b = bytes[i];
        if (b >= 0) {
            sb.appendCodePoint((int)b);
            priorWrongUtf8 = false;
        } else {
            int n = highBits(b); // Also # bytes in sequence
            boolean isUTF8 = !priorWrongUtf8
                    && 1 < n && n <= 6
                    && i + n <= bytes.length;
            if (isUTF8) {
                for (int j = 1; j < i + n; ++j) {
                     if (highBits(bytes[j]) != 1) {
                         isUTF8 = false;
                         break;
                     }
                }
            }
            if (isUTF8) {
                sb.append(new String(bytes, i, i + n, StandardCharsets.UTF_8));
                i += n - 1;
            } else {
                // UTF-8 Continuation char must be Cp1252.
                sb.append(new String(bytes, i, i + 1, "Windows-1251"));
            }
            priorWrongUtf8 = !isUTF8;
        }
    }
}

private int highBits(byte b) {
    int n = 0;
    while (n < 8 && ((1 << (7 - n)) & b) != 0) {
        ++n;
    }
    return n;
}