在做一个邮件程序,求一个正则表达式
字串1:=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?=
上面这个字串用如下的正则可以分解出:字符集、编码方式、内容。
正则: string strRegEx=@"\=\?(?<Charset>\S+)\?(?<Encoding>\w)\?(?<Content>\S+)\?\=";
但如果有重复的字串,如下面的:
=?utf-8?Q?=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698?==?utf-8?Q?=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82?=
就无法用上面的正则解析了,请问高手,如何写一个正则,能同时适用上面两种情况,且遇到第二种情况时,能把内容相加,而字符集和编码方式不加。
字串1:=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?=
上面这个字串用如下的正则可以分解出:字符集、编码方式、内容。
正则: string strRegEx=@"\=\?(?<Charset>\S+)\?(?<Encoding>\w)\?(?<Content>\S+)\?\=";
但如果有重复的字串,如下面的:
=?utf-8?Q?=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698?==?utf-8?Q?=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82?=
就无法用上面的正则解析了,请问高手,如何写一个正则,能同时适用上面两种情况,且遇到第二种情况时,能把内容相加,而字符集和编码方式不加。
MatchCollection mc = Regex.Matches(test, @"\=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?(?<Content>[^?]*)\?\=");
foreach (Match m in mc)
{
richTextBox1.Text += m.Groups["Charset"].Value + "\n";
richTextBox1.Text += m.Groups["Encoding"].Value + "\n";
richTextBox1.Text += m.Groups["Content"].Value + "\n";
}
输出:
utf-8
Q
=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698
utf-8
Q
=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82
基本上就是这个意思了,但是只需要Content的值相加,Charset和Encoding不需要相加,还有,不知道你上面的正则在下面情况下也是正确的吗?
string test="=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?="
请大侠再次赐教,非常感谢。
楼主自己试下就知道了,这种情况的结果是
GB2312
B
vfHEv7HqobDT0brDxvPStaGxzNi/rw==
我大致明白楼主Content的值相加的意思,但是不知道衔接部分的规则,所以还需要楼主把第二种情况的结果给出来我看下
这是我猜测的结果,楼主看下对不对string test = "=?utf-8?Q?=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698?==?utf-8?Q?=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82?=";
//string test = "=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?=";
test = Regex.Replace(test, @"\?==\?[^?]*\?\w\?", "");
MatchCollection mc = Regex.Matches(test, @"\=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?(?<Content>[^?]*)\?\=");
foreach (Match m in mc)
{
richTextBox1.Text += m.Groups["Charset"].Value + "\n";
richTextBox1.Text += m.Groups["Encoding"].Value + "\n";
richTextBox1.Text += m.Groups["Content"].Value + "\n";
}
//输出
utf-8
Q
=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82
因为楼主只要一组结果,所以可以这样写,那就把匹配不成功的情况考虑进去了string test = "=?utf-8?Q?=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698?==?utf-8?Q?=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82?=";
//string test = "=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?=";
test = Regex.Replace(test, @"\?==\?[^?]*\?\w\?", "");
Match m = Regex.Match(test, @"\=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?(?<Content>[^?]*)\?\=");
if (m.Success)
{
richTextBox1.Text += m.Groups["Charset"].Value + "\n";
richTextBox1.Text += m.Groups["Encoding"].Value + "\n";
richTextBox1.Text += m.Groups["Content"].Value + "\n";
}
else
{
richTextBox1.Text += "匹配不成功!";
}
大侠真是高手啊,不用我多说,就知道小弟想要怎么样的效果。
上面您写的正则完全符合要求,但现在有一种特殊情况,如下面:
string test="Yahoo! =?BIG5?B?wXC3+Q==?=: =?BIG5?B?p0Gkd7NRwdy90A==?=! =?BIG5?B?pd+nWaVbpEo=?= a717fe877 .";也就是在第一个 =? 之前有一个串:Yahoo! ,在最后面一个 ?= 的后面有一个串:a717fe877 .这两个串是没有被编码的,要单独提取出来,正则要怎么写?
也即:最后取得的Content应该等于第一个=?之前的串 + 您上面的正则取的串 + 最后一个?=之后的串
当然,这是特殊情况,大部分情况下用您上面的正则就可以了。
请大侠再次赐教,不胜感激。
按你的需求,换了种思路,看下是不是你要的结果吧
//string test = "=?utf-8?Q?=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698?==?utf-8?Q?=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82?=";
//string test = "=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?=";
string test = "Yahoo! =?BIG5?B?wXC3+Q==?=: =?BIG5?B?p0Gkd7NRwdy90A==?=! =?BIG5?B?pd+nWaVbpEo=?= a717fe877 .";
string Charset = "";
string Encoding = "";
string Content = "";
Content = Regex.Replace(test, @"(\?=[^=]*)?=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?|\?=", delegate(Match m) { if (m.Groups["Charset"].Value.Trim() != "") { Charset = m.Groups["Charset"].Value; Encoding = m.Groups["Encoding"].Value; } return ""; });
if (Charset != "")
{
richTextBox1.Text += Charset + "\n";
richTextBox1.Text += Encoding + "\n";
richTextBox1.Text += Content + "\n";
}
else
{
richTextBox1.Text += "匹配不成功!";
}目前只能晚上上网,所以如果上面的不符合要求,或是又有新的形式,楼主记得给出你要的结果,否则我就只能靠猜了^o^
大哥真乃神人也,对小弟的意图了解的一清二楚。
您上面写的正则基本符合要求,只是我忘记说明一点,看如下字串:
string test = "Yahoo! =?BIG5?B?wXC3+Q==?=: =?BIG5?B?p0Gkd7NRwdy90A==?=! =?BIG5?B?pd+nWaVbpEo=?= a717fe877 .";
大哥看到了吗?每个编码的字串是以 =? 开始,以 ?= 结束,不在此中间的都是未编码的字串。您上面写的正则可以提取出首、尾未编码的字串,但中间的没有提取出来。未编码的字串已用红色标明。还有,您上面的结果是全部拼在一起的,这样无法解码,我需要如下的结果:定义解码函数:
public static string DecodeText(string strText,string Charset,string Encoding)然后,用你的正则取得数据,应该是一个数组,其间有未编码的,也有已编码的,如果是已编码的,要提取出Charset 和 Encoding,然后,我会做如下处理:
string Result
for(,,)//这里是用正则提取到的数据
{
if(如果是未编码的数据)Result+=未编码的数据;
if(如果是已编码的数据)Result+=DecodeText(已编码的数据,Charset,Encoding);//调用解码函数
}
return Result;
当然也要兼顾到最标准的模式,即只有已编码的数据,且只有一段的,如
string test = "=?GB2312?B?vfHEv7HqobDT0brDxvPStaGxzNi/rw==?=";
也有可能是我第二次提到的情况,即都已编码,但分段的,如
string test = "=?utf-8?Q?=E6=84=9F=E8=B0=A2=E6=82=A8=E5=9C=A8=E7=8C=AA=E5=85=AB=E6=88=92=E7=BD=91=E9=80=89=E5=AE=9A9698?==?utf-8?Q?=E5=8F=B7=E4=BB=BB=E5=8A=A1=E4=B8=AD=E6=A0=87=E4=BD=9C=E5=93=81=EF=BC=8C=E8=AF=B7=E7=A1=AE=E8=AE=A4=E4=BB=BB=E5=8A=A1=E5=AE=8C=E6=88=90=E3=80=82?=";
也有这次提到的情况,即编码数据和未编码数据混杂,且多段。
还有最简单的情况,即没有编码
请大侠再次出手赐教,不胜感激。
foreach (string s in test)
{
string result = Regex.Replace(s, @"\=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?(?<Content>[^?]*)\?\=", delegate(Match m) { return DecodeText(m.Groups["Content"].Value, m.Groups["Charset"].Value, m.Groups["Encoding"].Value); });
richTextBox1.Text += result + "\n\n";
}
//输出:
已解码已解码已解码Yahoo! 已解码: 已解码! 已解码 a717fe877 .only a test.不知道楼主解码函数的内容,我这里用下面的代替了
public static string DecodeText(string strText, string Charset, string Encoding)
{
return "已解码";
}楼主的问题,如果不算上解码函数的话,其实就一行代码而已
string result = Regex.Replace(s, @"\=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?(?<Content>[^?]*)\?\=", delegate(Match m) { return DecodeText(m.Groups["Content"].Value, m.Groups["Charset"].Value, m.Groups["Encoding"].Value); });当然,上面写的正则默认为你的编码后的内容中没有“?”,如果可能存在,正则替换为
string result = Regex.Replace(s, @"\=\?(?<Charset>[^?]*)\?(?<Encoding>\w)\?(?<Content>((?!\?\=)[\s\S])*)\?\=", delegate(Match m) { return DecodeText(m.Groups["Content"].Value, m.Groups["Charset"].Value, m.Groups["Encoding"].Value); });
如果确认编码后的内容中不会存在“?”,那么就用前面的就可以了,后面这个会降低效率