字符串分割出现汉字乱码

kaoba 2008-11-09 10:19:21
下面我写的程序是用中文逗号和英文逗号来分割字符串,但是有些汉字却在显示时出现乱码现象,如“矛,连,模,态”等这些汉字总是用问号等字符显示。我自己初步的猜想是:由于这些汉字高八位恰好和某些Ascall码的一个字节的字符相匹配,所以显示不正确。但是怎么才能克服这种现象呢?
有没有人做过类似这种程序,麻烦给出解决方法,最好贴上原代码。
还有几个问题,用标准C++编写的程序是处理什么编码,UTF-8还是GBK还是其他编码格式?从数据库中读取的字段值是什么编码?从文本文件中读取的内容又是什么编码?谢谢了。
#include<string>
#include<iostream>
#include<vector>
using namespace std;

vector<string> Split(string &s)
{
string::size_type pos=0, pre_pos=0;
string tempword;
vector<string> TermVec;
while((pos=s.find_first_of(",,",pos))!=string::npos)
{
tempword=s.substr(pre_pos,pos-pre_pos);

tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ')+1);
if(tempword.size()==0){pre_pos=++pos; continue;}

TermVec.push_back(tempword);
pre_pos=++pos;
}
tempword=s.substr(pre_pos,pos-pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ')+1);
if(tempword.size()!=0)
TermVec.push_back(tempword);
return TermVec;
}
void main()
{
string s="我们是很好的朋友,可是有的时候却少不了闹矛盾,就连她都认为是不好的";
vector<string> vec=Split(s);
for(vector<string>::iterator iter=vec.begin();iter!=vec.end();iter++)
{cout<<*iter<<endl;}
}
...全文
644 27 打赏 收藏 转发到动态 举报
写回复
用AI写文章
27 条回复
切换为时间正序
请发表友善的回复…
发表回复
kaoba 2008-11-11
  • 打赏
  • 举报
回复
是出现错误了。刚才试错了
[Quote=引用 21 楼 kaoba 的回复:]
我用你之前给的程序试了“了埃琣闹 ”,正确着呢。
而你说的UltraEdit中出现的问题, 可能是它在查找字符时自身出现的问题吧。
引用 15 楼 nhycf 的回复:
你有UltraEdit 32吗?
不信你输入:
了埃琣闹

然后在查找对话框查找中文的逗号,结果就找到了。

因此要挨个依次查找才行。
算法可能要做重大调整才行。源码稍后附上
[/Quote]
kaoba 2008-11-11
  • 打赏
  • 举报
回复
我用你之前给的程序试了“了埃琣闹 ”,正确着呢。
而你说的UltraEdit中出现的问题, 可能是它在查找字符时自身出现的问题吧。
[Quote=引用 15 楼 nhycf 的回复:]
你有UltraEdit 32吗?
不信你输入:
了埃琣闹

然后在查找对话框查找中文的逗号,结果就找到了。

因此要挨个依次查找才行。
算法可能要做重大调整才行。源码稍后附上
[/Quote]
kaoba 2008-11-11
  • 打赏
  • 举报
回复
OK.感谢各位精彩回复。我要结帖了。哈哈。以后多交流交流啊。
潘李亮 2008-11-11
  • 打赏
  • 举报
回复
又一个不懂编码格式的。
nhycf 2008-11-11
  • 打赏
  • 举报
回复
又想起一则:

朱月坡
一先生发试卷,喊曰:“朱肚皮!”,数声,无应者。遂至之一侧。试卷发毕,止剩一张,问曰:“谁没有领到?”一女生站而曰:“我叫朱月坡”
nhycf 2008-11-11
  • 打赏
  • 举报
回复
关于拆分不当,我想起了两则笑话:

专业和尚
  某农村糊涂县长,一日做报告,咬文嚼字,照本宣科。
  当念至:“已获得文凭的和尚未获得文凭的干部……”
  读曰:“已获得文凭的和尚,未获得文凭的干部”引得台下哄堂大笑。
  领导怒曰:“有什么好笑的?和尚都可以取得文凭,干部就更要努力喽!”

用“一直”来造句:
我画了一直线。
编程-鸟人-_-- 2008-11-11
  • 打赏
  • 举报
回复
其实这类问题就是字符转换问题!!!
可以使用win32API函数,将UNICODE转换一下!!!

WideCharToMultiByte()
nhycf 2008-11-10
  • 打赏
  • 举报
回复
[Quote=引用 19 楼 hzc191025 的回复:]
楼主考虑的不够周到,我修改了下,你可以测试下!呵呵


C/C++ code
#include <string>
#include <iostream>
#include <vector>
#include "Windows.h"
using namespace std;

vector <string> Split(string &s)
{
string::size_type pos=0, pre_pos=0;
string tempword;
vector <string> TermVec;

char huang[] = ",";
char huang1[] = "矛";

string::size_type pos1 = 0, p…
[/Quote]
这位朋友,你这段代码能处理以下这句吗:

我们是很好的朋友,可是埃琣有的
hzc191025 2008-11-10
  • 打赏
  • 举报
回复
楼主考虑的不够周到,我修改了下,你可以测试下!呵呵


#include <string>
#include <iostream>
#include <vector>
#include "Windows.h"
using namespace std;

vector <string> Split(string &s)
{
string::size_type pos=0, pre_pos=0;
string tempword;
vector <string> TermVec;

char huang[] = ",";
char huang1[] = "矛";

string::size_type pos1 = 0, pos2 = 0;

while((pos = (pos1 = s.find(',', pos)) > (pos2 = s.find(",", pos)) ? pos2 : pos1) != string::npos )
// 这里不能使用楼主原来的函数,原来的函数都是针对单个字符的,如果是中文的逗号就会出现高字节匹配的问题
// while((pos = s.find_first_of(",,", pos)) != string::npos)
{
tempword = s.substr(pre_pos, pos-pre_pos);

tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ') + 1);

if(tempword.size()==0){ pre_pos = ++pos; continue;}

TermVec.push_back(tempword);

if (IsDBCSLeadByte(s[pos]))// 这里主要使用了windows的API,判断当前字节是不是双字节字符
{
pos += 2;
pre_pos = pos;
}
else
{
pre_pos=++pos;
}


}

tempword=s.substr(pre_pos,pos-pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ')+1);

if(tempword.size()!=0)
TermVec.push_back(tempword);
return TermVec;
}
void main()
{
string s="我们是很好的朋友,可是有的时候却少不了闹矛盾,真好的,就连她都认为是不好的";
vector <string> vec=Split(s);

for(vector <string>::iterator iter=vec.begin();iter!=vec.end();iter++)
{cout <<*iter <<endl;}
}
nhycf 2008-11-10
  • 打赏
  • 举报
回复
#include <string>
#include <iostream>
#include <vector>
using namespace std;

vector<string> Split(string &s)
{
string::size_type pos=0, pre_pos=0;
string tempword;
vector <string> TermVec;

while(s[pos])
{
if(s[pos] == ',' || *(unsigned short *)&s[pos] == 0xaca3) // 逗号
{
tempword = s.substr(pre_pos, pos - pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ') + 1);
if(s[pos] < 0)
++ pos;
pre_pos = ++ pos;
if(tempword.size())
TermVec.push_back(tempword);
}
else
{
if(s[pos] < 0)
++ pos;
++ pos;
}
}
tempword=s.substr(pre_pos,pos-pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ')+1);
if(tempword.size())
TermVec.push_back(tempword);
return TermVec;
}
void main()
{
string s = "我们是很好的朋友 , 时间片, 连接 , 却少不了埃琣闹矛盾,可是有的时候,,就连她都认为是不好的";
vector <string> vec = Split(s);
for(vector <string>::iterator i = vec.begin(); i!=vec.end();i++)
cout << *i <<endl;
}

不致就是这样了
kaoba 2008-11-10
  • 打赏
  • 举报
回复
感谢各位热心帮助。
nhycf 2008-11-10
  • 打赏
  • 举报
回复
#include <string>
#include <iostream>
#include <vector>
using namespace std;

vector<string> Split(string &s)
{
string::size_type pos=0, pre_pos=0;
string tempword;
vector <string> TermVec;

while(s[pos])//(pos = s.find_first_of(",,", pos)) != string::npos)
{
if(s[pos] != ',' && *(unsigned short *)&s[pos] != 0xaca3)
{
if(s[pos] < 0)
++ pos;
pos ++;
continue;
}

tempword=s.substr(pre_pos, pos - pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ') + 1);
if(s[pos] < 0)
++ pos;
pre_pos = ++ pos;
if(!tempword.size())
continue;

TermVec.push_back(tempword);
}
tempword=s.substr(pre_pos,pos-pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ')+1);
if(tempword.size())
TermVec.push_back(tempword);
return TermVec;
}
void main()
{
string s = "我们是很好的朋友,时间片,连接,却少不了埃琣闹矛盾,可是有的时候,,就连她都认为是不好的";
vector <string> vec = Split(s);
for(vector <string>::iterator i = vec.begin(); i!=vec.end();i++)
cout << *i <<endl;
}

初步版本就是这样,你最好能尽快回复,否则有改进版本的话,我也发不上。(论坛不能连续发三篇以上的贴子)
nhycf 2008-11-10
  • 打赏
  • 举报
回复
你有UltraEdit 32吗?
不信你输入:
了埃琣闹

然后在查找对话框查找中文的逗号,结果就找到了。

因此要挨个依次查找才行。
算法可能要做重大调整才行。源码稍后附上
nhycf 2008-11-10
  • 打赏
  • 举报
回复
pos += 2;
改为:pos ++;
0xaca3就是逗号的内码
kaoba 2008-11-10
  • 打赏
  • 举报
回复
想问nhycf下面的*(unsigned short *)&s[pos] != 0xaca3是什么意思。
if(s[pos] < 0 && *(unsigned short *)&s[pos] != 0xaca3)
{
pos += 2;
continue;
}
当string s = "我们是很好的朋友,时间片,连接,可是有的时候却少不了闹矛盾,就连她都认为是不好的"时,“时间片,连接”无法用逗号分开。能不能改进一下。
nhycf 2008-11-10
  • 打赏
  • 举报
回复
调整一下语句次序:
		if(s[pos] < 0 && *(unsigned short *)&s[pos] != 0xaca3)
{
pos += 2;
continue;
}
tempword=s.substr(pre_pos, pos - pre_pos);
nhycf 2008-11-10
  • 打赏
  • 举报
回复
在MFC中,数据库中读取的字段值默认都是ANSI编码的
elemem 2008-11-10
  • 打赏
  • 举报
回复
字符处理好复杂,特别是牵涉到编码格式的时候,帮忙顶下
nhycf 2008-11-10
  • 打赏
  • 举报
回复
C++编译器内置支持ANSI及unicode编码.
文本常用的有两种:最普遍的是ANSI,第二种是以ff fe开头的为unicode编码。只要能处理这两种常见的格式基本上是没有问题的。
即使遇上UTF-8及其他格式,可以先用工具进行转换。
nhycf 2008-11-10
  • 打赏
  • 举报
回复
#include <string>
#include <iostream>
#include <vector>
using namespace std;

vector <string> Split(string &s)
{
string::size_type pos=0, pre_pos=0;
string tempword;
vector <string> TermVec;

while((pos=s.find_first_of(",,", pos)) != string::npos)
{
tempword=s.substr(pre_pos, pos - pre_pos);
if(s[pos] < 0 && *(unsigned short *)&s[pos] != 0xaca3)
{
pos += 2;
continue;
}

tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ') + 1);
if(s[pos] < 0)
++ pos;
pre_pos = ++ pos;
if(!tempword.size())
continue;

TermVec.push_back(tempword);
}
tempword=s.substr(pre_pos,pos-pre_pos);
tempword.erase(0,tempword.find_first_not_of(' '));
tempword.erase(tempword.find_last_not_of(' ')+1);
if(tempword.size())
TermVec.push_back(tempword);
return TermVec;
}
void main()
{
string s = "我们是很好的朋友,可是有的时候却少不了闹矛盾,就连她都认为是不好的";
vector <string> vec=Split(s);
for(vector <string>::iterator iter=vec.begin();iter!=vec.end();iter++)
cout << *iter <<endl;
}

重发
加载更多回复(7)

65,211

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧