主题:百度Astar2006程序设计大赛预赛题--百度语言翻译机
zwj1207
[专家分:40] 发布于 2006-05-27 10:32:00
注册过的朋友请到http://star.baidu.com 答题
1.百度语言翻译机
百度的工程师们是非常注重效率的,在长期的开发与测试过程中,他们逐渐创造了一套独特的缩略语。他们在平时的交谈、会议,甚至在各种技术文档中都会大量运用。
为了让新员工可以更快地适应百度的文化,更好地阅读公司的技术文档,人力资源部决定开发一套专用的翻译系统,把相关文档中的缩略语和专有名词翻译成日常语言。
输入要求:
输入数据包含三部分:
1. 第一行包含一个整数N(N<=10000),表示总共有多少个缩略语的词条;
2. 紧接着有N行的输入,每行包含两个字符串,以空格隔开。第一个字符串为缩略语(仅包含大写英文字符,长度不超过10字节),第二个字符串为日常语言(不包含空格,长度不超过255字节);
3. 从第N+2开始到输入结束为包含缩略语的相关文档(总长度不超过1000000个字节)。例:
6
PS 门户搜索部
NLP 自然语言处理
PM 产品市场部
HR 人力资源部
PMD 产品推广部
MD 市场发展部
百度的部门包括PS,PM,HR,PMD,MD等等,其中PS还包括NLP小组。
输出要求:
输出将缩略语转换成日常语言后的文档。(将缩略语转换成日常语言,其他字符保留原样)。例:
百度的部门包括门户搜索部,产品市场部,人力资源部,产品推广部,市场发展部等等,其中门户搜索部还包括自然语言处理小组。
评分规则:
1.程序将运行在一台Linux机器上(内存使用不作严格限制),在每一测试用例上运行不能超过10秒,否则该用例不得分;
2.要求程序能按照输入样例的格式读取数据文件,按照输出样例的格式将运行结果输出到标准输出上。如果不能正确读入数据和输出数据,该题将不得分;
3.该题目共有4个测试用例,每个测试用例为一个输入文件。各测试用例占该题目分数的比例分别为25%,25%,25%,25%;
4.该题目20分。
注意事项:
1.输入数据是中英文混合的,中文采用GBK编码。
GBK:是又一个汉字编码标准,全称《汉字内码扩展规范》。采用双字节表示,总体编码范围为 8140-FEFE,首字节在 81-FE 之间,尾字节在 40-FE 之间,排除xx7F。总计 23940 个码位,共收入 21886 个汉字和图形符号,其中汉字(包括部首和构件)21003 个,图形符号 883 个。
2.为保证答案的唯一性,缩略语的转换采用正向最大匹配(从左到右为正方向)原则。请注意样例中PMD的翻译。
回复列表 (共8个回复)
沙发
goal00001111 [专家分:4030] 发布于 2006-05-28 17:22:00
/*
算法介绍:
1。创建一个language结构,它包含两个字符串,分别用来存储大写字母串和对应的中文。
2。读入数据N,大写字母串和对应的中文(存储到*lan),包含缩略语的相关文档(存储到textBefore[lenText])。
3。遍历textBefore[lenText],将转换成日常语言后的文档存储到textAfter[lenText],转换的格式为:
如果是汉字则不转换,直接写入textAfter[lenText];
如果为大写字母,则将其提取,存储到eng[lenEng],遍历lan,寻找与eng[lenEng]匹配的English[lenEng],
将对应的Chinese[lenChi]存储到chi[lenChi];然后把chi[lenChi]接到textAfter[lenText]。
4。输出textAfter[lenText]。
*/
#include <iostream>
#include<string>
#include<fstream>
#include <time.h>
using namespace std;
const int lenEng = 11;
const int lenChi = 256;
const long lenText = 100001;
typedef struct{
char English[lenEng];
char Chinese[lenChi];
} language;
language * Readata(const char *filename, char text[], language *lan, int & N);
bool IsUpper(char ch);
void PiPei(const language *lan, int len, const char *eng, char *chi);
void Transducer(const language *lan, int len, const char *textBefore);
int main()
{
time_t startTime;
time_t endTime;
time(&startTime);
language *lan;
char textBefore[lenText];
int N = 0;
lan = Readata("in1.txt", textBefore, lan, N);
//for (int i=0; i<N; i++)
// cout << lan[i].English << ' ' << lan[i].Chinese << endl;
// cout << textBefore << endl;
Transducer(lan, N, textBefore);
time(&endTime);
// cout << difftime(endTime, startTime) << endl;
getchar();
return 0;
}
void Transducer(const language *lan, int len, const char *textBefore)
{
char textAfter[lenText];
int topA = 0;
int topB = 0;
while(textBefore[topB])
{
while (textBefore[topB] && !IsUpper(textBefore[topB]))
{
textAfter[topA++] = textBefore[topB++];
}
textAfter[topA++] = '\0';
// cout << textAfter << endl;
char eng[lenEng];
int topE = 0;
while (textBefore[topB] && IsUpper(textBefore[topB]))
{
eng[topE++] = textBefore[topB++];
}
eng[topE++] = '\0';
if (textBefore[topB])
{
char chi[lenChi];
PiPei(lan, len, eng, chi);
strcat(textAfter, chi);
while(textAfter[topA])
topA++;
}
}
cout << textAfter;
}
void PiPei(const language *lan, int len, const char *eng, char *chi)
{
for (int i=0; i<len; i++)
{
if (strcmp(eng, lan[i].English) == 0)
{
strcpy(chi, lan[i].Chinese);
return ;
}
}
}
bool IsUpper(char ch)
{
if (ch >= 'A' && ch <= 'Z')
return true;
return false;
}
language * Readata(const char *filename, char text[], language *lan, int & N)
{
fstream in(filename);
if (!in)
return 0; //结束程序执行
in >> N;
lan = new language[N];
int top = 0;
int n = 0;
while (!in.eof() && n < N)
{
in >> lan[top].English;
in >> lan[top].Chinese;
top++;
n++;
}
char buf[lenText];
while (!in.eof())
{
in >> buf;
strcat(text, buf);
}
in.close(); //关闭文件
return lan;
}
板凳
if007 [专家分:650] 发布于 2006-05-28 18:50:00
我试了下你的程序,都是烫哦...
另外,我很有兴趣你关于区分"PM 产品市场部"和"PMD 产品推广部"的算法.
其实这题曾出过, 在东部牛仔(eastcowboy)的第25次编程比赛第一题上.就是拳皇游戏的那题,关于字符串匹配的.
3 楼
sarrow [专家分:35660] 发布于 2006-05-28 19:23:00
我试了下你的程序,都是烫哦...
[em10][em10][em10][em10][em10]
[em10][em10][em10][em10][em10]
[em10][em10][em10][em10][em10]
[em10][em10][em10][em10][em10]
[em10][em10][em10][em10][em10]
4 楼
fantasyzzz [专家分:0] 发布于 2006-05-31 11:25:00
#include<iostream>
#include<vector>
#include<algorithm>
#include<string>
using namespace std;
//1: 百度语言翻译机
vector<string> v1;
vector<string> v2;
bool IsUppercase(char c)
{
if(c>='A'&&c<='Z')
return true;
return false;
}
void Search(string source,string& dest)
{
if(source.empty())
return;
string temp;
int index;
int start=-1;
for(int i=0;i<source.length();++i)
{
for(int k=i;k<source.length();++k)
{
temp+=source[k];
for(int j=0;j<v1.size();++j)
if(temp==v1[j])
{
index=j;
start=i;
}
}
if(start==-1)
temp.clear();
else
{
for(int j=0;j<start;++j) //copy the elements at the start front
dest+=source[i];
dest+=v2[index];
temp.clear();
for(int j=start+v1[index].length();j<source.length();++j)
temp+=source[j];
Search(temp,dest);
return;
}
}
dest+=source;
}
void BLT(string str)
{
string dest;
v1.push_back("PS");
v1.push_back("NLP");
v1.push_back("PM");
v1.push_back("HR");
v1.push_back("PMD");
v1.push_back("MD");
v2.push_back("门户搜索部");
v2.push_back("自然语言处理");
v2.push_back("产品市场部");
v2.push_back("人力资源部");
v2.push_back("产品推广部");
v2.push_back("市场发展部");
string temp;
for(int i=0;i<str.length();++i)
{
if(!IsUppercase(str[i]))
{
if(!temp.empty())
Search(temp,dest);
dest+=str[i];
temp.clear();
}
else
temp+=str[i];
}
if(!temp.empty())
Search(temp,dest);
cout<<dest<<endl;
}
void main()
{
string str;
cin>>str;
BLT(str);
}
和题目要求的文件接口不一样,懒的去弄,请大家帮忙测试下,谢谢。。
5 楼
cforlinux [专家分:80] 发布于 2006-05-31 11:36:00
什麽叫都是 烫啊
6 楼
weensy [专家分:0] 发布于 2006-06-01 04:50:00
按理说允许用C++,那就等于可以用标准库,但是下面的代码没有通过,是0分,不知道什么原因,是程序哪里出了问题? 请大虾指点!
#include <string>
#include <iostream>
#include <fstream>
#include <queue>
using namespace std;
struct textMap
{
string breviaryText;
string originalText;
};
static int nMap;
static string text;
class Compare
{ //比较类
public:
bool operator() (const textMap& c1, const textMap& c2) const
{
return (c1.breviaryText.size() < c2.breviaryText.size());
}
};
priority_queue<textMap, vector<textMap>, Compare> priorityQueue;
void stringReplace(string & str, const string& des, const string& src)
{
string::size_type pos = 0;
string::size_type srclen = src.size();
string::size_type deslen = des.size();
while((pos=str.find(src, pos)) != string::npos)
{
str.replace(pos, srclen, des);
pos += deslen;
}
}
int main(int argc, char* argv[])
{
ifstream is(argv[1], ios::in | ios::binary);
is >> nMap;
textMap tempMap;
for(int i = 0; i < nMap; ++i)
{
is >> tempMap.breviaryText;
is >> tempMap.originalText;
priorityQueue.push(tempMap);
}
is >> text;
for(int i = 0; i < nMap; ++i)
{
tempMap = priorityQueue.top();
priorityQueue.pop();
stringReplace(text, tempMap.originalText, tempMap.breviaryText);
}
cout << text << endl;
return 0;
}
7 楼
npu007 [专家分:0] 发布于 2006-06-01 13:45:00
我的也只得0分,虽然感到奇怪,但我还是有预感.
因为测试中很可能文字是分段的,而我的程序没有考虑分段. 当初侥幸和偷懒,一下子损失这么多分.
实际上,第一道题我个人感觉应该是6道中最简单的一道.
8 楼
nevsaynevwk [专家分:0] 发布于 2006-06-13 10:37:00
什么叫都是烫哦?
我来回复