注意可能有重复的收件人。
version 1(20ms):
#include<cstdio>
#include<iostream>
#include<map>
#include<set>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn = 150,maxlen = 80;
char mes[maxlen];
map<string,string>mta;
string tf[maxn],tm[maxn];
void readmes(){
int i = 0;
getchar();
for(;;){
char c = getchar();
if(c != '*'){
mes[i++] = c;
if(c == '\n'){
int t = 5;
while(t--) mes[i++] = ' ';
}
}
else break;
}
mes[i] = 0;
}
int main(){
int n;
string a,b,t;
while(cin>>t && t[0] != '*'){
cin>>a>>n;
while(n--){
cin>>b;
mta[b] = a;
}
}
string uf,um;
while(cin>>t && t[0] != '*'){
int p = t.find('@',0);
uf = t.substr(0,p);
um = t.substr(p+1,t.length()-p+1);
int cnt = 0;
set<string>s;
while(cin>>t && t[0] != '*'){
if(s.count(t)) continue;
s.insert(t);
int p = t.find('@',0);
tf[cnt] = t.substr(0,p);
tm[cnt] = t.substr(p+1,t.length()-p+1);
cnt++;
}
readmes();
for(int i = 0;i < cnt;i++){
if(!tm[i][0]) continue;
cout<<"Connection between "<<um<<" and "<<tm[i]<<endl;
int mark = 0;
cout<<" HELO "<<um<<endl;
cout<<" 250\n";
cout<<" MAIL FROM:<"<<uf<<'@'<<um<<'>'<<endl;
cout<<" 250\n";
for(int j = i;j < cnt;j++){
if(tm[j] != tm[i]) continue;
cout<<" RCPT TO:<"<<tf[j]<<'@'<<tm[j]<<'>'<<endl;
if(mta.count(tf[j]) && mta[tf[j]] == tm[j]){
mark = 1;
cout<<" 250\n";
}
else cout<<" 550\n";
if(j != i) tm[j][0] = 0;
}
if(mark){
cout<<" DATA\n 354\n";
cout<<" "<<mes<<".\n 250\n";
}
cout<<" QUIT\n 221\n";
}
}
return 0;
}
version 2(0ms,参考书上的代码):
#include<iostream>
#include<map>
#include<set>
#include<vector>
#include<cstring>
#include<algorithm>
using namespace std;
void parse_addr(const string& s,string& mta,string& user){
int p = s.find('@',0);
user = s.substr(0,p);
mta = s.substr(p + 1);
}
int main(){
int n;
string mta,user,mta2,user2,t;
set<string>addr;
while(cin>>t && t[0] != '*'){
cin>>mta>>n;
while(n--){
cin>>user;
addr.insert(user + '@' + mta);
}
}
while(cin>>t && t[0] != '*'){
parse_addr(t,mta,user);
vector<string>mtas;
map<string,vector<string> >users;
set<string>sented;
while(cin>>t && t[0] != '*'){
if(sented.count(t)) continue; //消除重复的收件人
sented.insert(t);
parse_addr(t,mta2,user2);
if(!users.count(mta2)){
mtas.push_back(mta2);
users[mta2] = vector<string>();
}
users[mta2].push_back(t);
}
string mes;
getline(cin,t); //吃掉‘*’行的回车
//在每行的开头都加五个空格,比我之前的做法简便
while(getline(cin,t) && t[0] != '*') mes += " " + t +'\n';
for(int i = 0;i < mtas.size();i++){
cout<<"Connection between "<<mta<<" and "<<mtas[i]<<endl;
cout<<" HELO "<<mta<<endl;
cout<<" 250\n";
cout<<" MAIL FROM:<"<<user<<'@'<<mta<<">\n";
cout<<" 250\n";
int mark = 0;
vector<string>tu = users[mtas[i]];
for(int j = 0;j < tu.size();j++){
cout<<" RCPT TO:<"<<tu[j]<<">\n";
if(addr.count(tu[j])) { mark = 1;cout<<" 250\n";}
else cout<<" 550\n";
}
if(mark){
cout<<" DATA\n 354\n";
cout<<mes<<" .\n 250\n";
}
cout<<" QUIT\n 221\n";
}
}
return 0;
}