我目前正在使用以下代码下载HTML页面:
Try
Dim req As System.Net.HttpWebRequest = DirectCast(WebRequest.Create(URL), HttpWebRequest)
req.Method = "GET"
Dim resp As Net.HttpWebResponse = DirectCast(req.GetResponse(), Net.HttpWebResponse)
Dim stIn As IO.StreamReader = New IO.StreamReader(resp.GetResponseStream())
Dim strResponse As String = stIn.ReadToEnd
''Clean up
stIn.Close()
stIn.Dispose()
resp.Close()
Return strResponse
Catch ex As Exception
Return ""
End Try
这适用于大多数页面,但对于某些页面(例如:www.gap.com),我得到错误编码的响应。
例如,在gap.com中,我将“”改为“?”
更不用说如果我尝试加载google.cn会发生什么......
我在这里缺少什么,让.Net对此进行编码?
我最担心的是,我实际上必须读取HTML中指定编码的元标记,然后重新读取(重新编码?)整个流。
任何指针都将非常感激。
更新
感谢John Saunders的回复,我离我更近一点了。 HttpWebResponse.ContentEncoding属性似乎总是空的。但是,HttpWebResponse.CharacterSet似乎很有用,有了这段代码,我就越来越近了:
Dim resp As Net.HttpWebResponse = DirectCast(req.GetResponse(), Net.HttpWebResponse)
Dim respEncoding As Encoding = Encoding.GetEncoding(resp.CharacterSet)
Dim stIn As IO.StreamReader = New IO.StreamReader(resp.GetResponseStream(), respEncoding)
现在Google.cn与所有中文字符完美结合 但是,Gap.Com仍然出错了。
对于Gap.com,HttpWebResponse.CharacterSet是ISO-8859-1,我通过GetEncoding获取的编码是{System.Text.Latin1Encoding},其中的主体名称为“ISO-8859-1”,AND HTML中的Content-Type META标记指定为“charset = ISO-8859-1”。
我还在做错什么吗? 或者GAP做错了什么?
答案 0 :(得分:2)
我相信HttpWebResponse有一个ContentEncoding属性。在StreamReader的构造函数中使用它。
答案 1 :(得分:1)
Gap的网站错了。具体问题是他们的页面声称编码为Latin1(ISO-8859-1),而页面使用的字符#146在ISO-8859-1中无效。
然而,该字符在Windows CP-1252编码(ISO 8859-1的超集)中有效。在CP-1252中,字符代码#146用于右引号字符。你会在今天的Gap.com主页上的文章中看到这是“你会发现娇小和小尺寸”的撇号。
您可以阅读 http://en.wikipedia.org/wiki/Windows-1252了解详情。事实证明,这种事情是网页上常见的问题,其中内容最初是以CP-1252编码保存的(例如,从Word复制/粘贴)。
故事的道德:始终将国际化文本作为Unicode存储在数据库中,并始终在Web服务器上以HTML格式发出HTML!
答案 2 :(得分:0)
丹尼尔,
有些页面甚至没有返回CharacterSet
中的值,因此这种方法不太可靠。
有时甚至连浏览器都无法“猜测”使用哪种编码,所以我认为你不能做100%的enconding识别。
在我的特殊情况下,当我处理西班牙语或葡萄牙语页面时,我使用 UTF7 编码,它对我来说很好(áéíóúñÑêã...等)。
可能是您可以先加载一个CharacterSet代码表及其相应的编码。如果CharacterSet为空,您可以提供默认编码。
detectEncodingFromByteOrderMarks
构造函数中的StreamReader
参数可能会有所帮助,因为它会自动检测或推断出第一个字节的某些编码。