文号
t79858
阅读
2922
回复
0
收藏
1
【技巧】.NET中28591代码页的妙用
2016/05/07
IP:四川
认真学过C#或.NET的同学应该知道,在.NET中,string是以char组成的,而char则表示16位Unicode的字符,字节流则以byte[]表示。字节流要想变为字符串,就要进行解码(Encoding.GetString),而有时候我们并不想解码,而是按照C语言中习惯的方法使用这些字符串,这时候就需要使用28591代码页了。

28591代码页介绍:
在Windows和.NET中,28591代码页指ISO-8859-1编码,是一种曾经广泛用于UNIX操作系统的单字节编码标准。它针对ASCII进行了扩展,其中80-9F为扩展控制字符,A0-FF加入了西欧语言常用的扩展字符。它的特殊之处在于,Unicode制定时考虑与它兼容,因此Unicode前256个字符与它是完全一一对应的。也就是说,28591代码页将8位字符直接扩展为16位字符。这个性质让它在编程中非常有用。另外,28591是.NET框架原生支持的代码页,在Windows和Linux/UNIX中都能使用,不必担心不可用的问题。

28591应用场合:需要按字节操作,但需要string类提供的便利的时候。
/*
 * Created by SharpDevelop.
 * User: surface
 * Date: 04/11/2016
 * Time: 21:43
 * 
 * To change this template use Tools | Options | Coding | Edit Standard Headers.
 */
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Windows.Forms;
using System.Threading;
using System.Threading.Tasks;
using System.Text;
    
namespace mywinforms1234
{
    /// <summary>
    /// Description of MainForm.
    /// </summary>
    public partial class MainForm : Form
    {
        public MainForm()
        {
            //
            // The InitializeComponent() call is required for Windows Forms designer support.
            //
            InitializeComponent();
                
            //
            // TODO: Add constructor code after the InitializeComponent() call.
            //
        }
        void Button1Click(object sender, EventArgs e)
        {
            var arr_a = new byte[] { 0x80, 0x81, 0x82, 0x83 };
            var arr_b = new byte[] { 0x81, 0x82 };
            string a = Encoding.GetEncoding(28591).GetString(arr_a);
            string b = Encoding.GetEncoding(28591).GetString(arr_b);
            MessageBox.Show(a.Contains(b).ToString()); // 测试a是否包含b
        }
    }
}

/*
 * Created by SharpDevelop.
 * User: surface
 * Date: 2016/5/6
 * Time: 15:26
 * 
 * To change this template use Tools | Options | Coding | Edit Standard Headers.
 */
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Windows.Forms;
using System.Text;
using System.IO;
     
namespace encodingtest1
{
    /// <summary>
    /// Description of MainForm.
    /// </summary>
    public partial class MainForm : Form
    {
        public MainForm()
        {
            //
            // The InitializeComponent() call is required for Windows Forms designer support.
            //
            InitializeComponent();
                 
            //
            // TODO: Add constructor code after the InitializeComponent() call.
            //
        }
        void Button1Click(object sender, EventArgs e)
        {
            // 示例文本
            string sampletxt = "sssaaa\r\n我是中文测试一二三四五\r\n";
                 
            // 写入示例文本,注意.NET默认写入的文本有BOM
            File.WriteAllText("abc.txt", sampletxt, Encoding.UTF8);
                 
            // 注意一定要将detectEncodingFromByteOrderMarks关掉,否则会受BOM影响而失效
            string content = "";
            using (StreamReader sr =
                   new StreamReader("abc.txt", Encoding.GetEncoding(28591), false))
            {
                content = sr.ReadToEnd();
                MessageBox.Show(content);
                //content = content.Replace("\u00ef\u00bb\u00bf", "");
                if (content.StartsWith("\u00ef\u00bb\u00bf")) // 如果有BOM的话
                    content = content.Substring(3); // 去掉bom
                MessageBox.Show(content);
            }
                 
            // 重新写入修改过的内容
            using (StreamWriter sw =
                   new StreamWriter("abc.txt", false, Encoding.GetEncoding(28591)))
            {
                sw.Write(content);
            }
                 
            // 再次测试有无BOM
            using (StreamReader sr =
                   new StreamReader("abc.txt", Encoding.GetEncoding(28591), false))
            {
                content = sr.ReadToEnd();
                MessageBox.Show(content);
            }
                 
            // 如果单纯是为了写入无BOM的UTF-8文件,不用这么麻烦,这样就可以了
            File.WriteAllBytes("abc.txt", Encoding.UTF8.GetBytes(sampletxt));
                 
            // 再次测试有无BOM
            using (StreamReader sr =
                   new StreamReader("abc.txt", Encoding.GetEncoding(28591), false))
            {
                content = sr.ReadToEnd();
                MessageBox.Show(content);
            }
        }
    }
}
[ 修改于10年7个月前 - 2016/05/07 23:59:11 ]
笔记
{{note.content}}
{{n.user.username}}
{{fromNow(n.toc)}} {{n.status === noteStatus.disabled ? "已屏蔽" : ""}} {{n.status === noteStatus.unknown ? "正在审核" : ""}} {{n.status === noteStatus.deleted ? '已删除' : ''}}
  • 编辑
  • 删除
  • {{n.status === 'disabled' ? "解除屏蔽" : "屏蔽" }}
我也是有底线的