#include <iostream>
#include <string>
#include <algorithm>
#include <vector>
#include <stack>
#include <random>
#include <type_traits>
#include <string_view>
#include <assert.h>
#include <array>
#include <tuple>
#include <unordered_map>
#include <functional>
#include <queue>
#include <map>
#include <iomanip>
using namespace std;
unordered_map<int,vector<string>> keywords;
vector<string> content;
inline void init() // init for kerword
{
keywords[3]={"WoCao","Bing!","OttO","Hello World!","Space","LeagueOfLegends","Codeforces","Leetcode"};
keywords[4]={"male","female","?"};
keywords[5]={"不知道起啥名","无名","丁真"};
keywords[6]={"Wang","Li","Bin","Faker","理塘"};
}
namespace jug{
template<typename T>
struct is_value
{
static constexpr bool value=false;
};
template <>
struct is_value<double>
{
static constexpr bool value=true;
};
template <>
struct is_value<float>
{
static constexpr bool value=true;
};
template <>
struct is_value<int>
{
static constexpr bool value=true;
};
template <>
struct is_value<size_t>
{
static constexpr bool value=true;
};
template<>
struct is_value<long long>
{
static constexpr bool value=true;
};
template<>
struct is_value<uint64_t>
{
static constexpr bool value=true;
};
};
template<typename T>
inline T get_random_number(T l,T r) //Generate a new random number
{
static_assert(jug::is_value<T>::value,"Wrong type!Type must be numerical value!");
assert(r>=l);
static mt19937 Engine(random_device{}());
if constexpr (is_integral<T>::value)
{
uniform_int_distribution<T> gain_number(l,r);
return gain_number(Engine);
}
else{
uniform_real_distribution<T> gain_number(l,r);
return gain_number(Engine);
}
}
class Search_for_keyword_And_Generate_warning
{
protected:
void throw_mistake(const size_t line,string&& warning=""){
if(!warning.empty())
{
warning+=" on line "+to_string(line+1);
cout<<warning<<'\n';
throw invalid_argument(warning);
return;
}
cout<<"invalid char on line "<<line+1<<endl;
throw invalid_argument("invalid char!");
};
inline bool spacejudge(char it)
{
return it=='\t'||it==' ';
}
void detector(const string &it,size_t iter,const size_t line)
{
if(it.substr(iter,3)!=")}}") throw_mistake(line,"Your instruction generates mistake");
}
void match_RightParenthese(const string &it,size_t &pos,size_t line)
{
while(it[pos]!='('&&pos<it.size())
{
if(it[pos]!=' ') throw_mistake(line,"Your instruction generates mistake");
pos++;
}
if(pos>=it.size()) throw_mistake(line,"expected a right match '('");
pos+=1;
}
public:
const tuple<double,double,size_t,int> keyword_getvalue(const string &it,size_t iter,const size_t line)
{
double l{},r=-1;
size_t status=0,i;int floating_num=10;
int negative_char_number{};
match_RightParenthese(it,iter,line);
for(i=iter;it[i]!=')'&&i<it.size();i++){
if(spacejudge(it[i])) continue;
if(!(isdigit(it[i])||it[i]==','||it[i]=='.'||it[i]=='-')) throw_mistake(line);
if(it[i]=='-') ++negative_char_number;
switch(status){
case 0: {if(isdigit(it[i])||it[i]=='-') l=atof(it.c_str()+i);++status;break;}
case 1: {if(it[i]==',') ++status;break;}
case 2: {if(isdigit(it[i])||it[i]=='-') r=atof(it.c_str()+i);++status;break;}
case 3: {if(it[i]==',') ++status;break;}
case 4: {if(isdigit(it[i])||it[i]=='-') floating_num=atoi(it.c_str()+i);++status;break;}
case 5: {if(it[i]==',') throw_mistake(line);break;}
}
}
if(floating_num<0) throw_mistake(line,"The number of point's show must be >=0");
if(negative_char_number>2) throw_mistake(line);
if(r==-1) r=l;
if(l==0 and r!=0) throw_mistake(line);
return {l,r,i,floating_num};
}
size_t keyword_getlen(const string &it,size_t iter,const size_t line)
{
match_RightParenthese(it,iter,line);
if(it[iter]!=')') throw_mistake(line);
//detector(it,iter,line);
return iter;
}
pair<vector<string>,size_t> keyword_random(const string &it,size_t iter,const size_t line)
{
size_t i=iter+6;
bool string_mode=false;
match_RightParenthese(it,i,line);
if(it[i]==',') throw_mistake(line);
vector<string> temp_space;
temp_space.reserve(5);
string t;
while(it[i]!=')'||string_mode==true){
if(it[i]=='"') string_mode=!string_mode;
if(it[i]==',')
{
temp_space.emplace_back(t);
t.clear();
}
else t.push_back(it[i]);
i++;
}
temp_space.shrink_to_fit();
return make_pair(temp_space,i);
}
};
struct attribute
{
unsigned int max_len=-1,order=0;
double min_val=0,max_val=0;
int max_out_floating=0;
vector<string> rd_array={};
};
class compiler:public Search_for_keyword_And_Generate_warning
{
private:
vector<array<int,2>> right_bracket;
map<int,unordered_map<int,attribute>> modify_place;
static int left_bracket_num;
static constexpr char *email_char_list="abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890";
size_t repeat_out(int MIN1,int MIN2,size_t __begin,size_t _floor)
{
function<void(size_t&)> begin_init=[&](size_t &_begin)
{
while(_begin<content[MIN1].size()&&content[MIN1][_begin]!='\'')
++_begin;
};
begin_init(__begin);int p{},new_offset{_floor};
bool repeat_leap{false},flag{true};size_t increment{};
for(size_t index=0;index<MIN2;++index){
bool convert_=false;new_offset=_floor;
for(int k=MIN1;k<=right_bracket[_floor][0];k++){
bool next_line=true;
if(!repeat_leap) p=(k==MIN1?__begin+1:0);
repeat_leap=false;
for(;p<content[k].size();p++){
if(!convert_&&content[k][p]=='{') ++new_offset;
if(!convert_&&flag&&content[k][p]=='{') ++increment;
if(content[k][p]=='\'') convert_=!convert_;
if(p-1>=0&&(convert_&&(((content[k][p]=='{'&&content[k][p+1]=='{')||(content[k][p]=='{' && content[k][p-1]=='{'))||((content[k][p]=='}' && content[k][p+1]=='}')||(content[k][p]=='}'&&content[k][p-1]=='}')))))
continue;
if(modify_place[k][p].order){
switch(modify_place[k][p].order){
case 1:{cout<<fixed<<setprecision(modify_place[k][p].max_out_floating)<<get_random_number(modify_place[k][p].min_val,modify_place[k][p].max_val),p=modify_place[k][p].max_len;break;}
case 2:{
int t__t=get_random_number<int>(0,modify_place[k][p].rd_array.size()-1);
cout<<modify_place[k][p].rd_array[t__t];
p=modify_place[k][p].max_len;
break;
}
case 3:{
int t_t=get_random_number<int>(0,keywords[3].size()-1);
cout<<keywords[3][t_t];
p=modify_place[k][p].max_len;
break;
}
case 4:{
int t_t=get_random_number<int>(0,keywords[4].size()-1);
cout<<keywords[4][t_t];
p=modify_place[k][p].max_len;
break;
}
case 5:{
int t_t=get_random_number<int>(0,keywords[5].size()-1);
cout<<keywords[5][t_t];
p=modify_place[k][p].max_len;
break;
}
case 6:{
int t_t=get_random_number<int>(0,keywords[6].size()-1);
cout<<keywords[6][t_t];
p=modify_place[k][p].max_len;
break;
}
case 7:{
int _biggest_recursive_num=get_random_number(static_cast<int>(modify_place[k][p].min_val),static_cast<int>(modify_place[k][p].max_val));
if(convert_) convert_=false;
if(_biggest_recursive_num>0){if(new_offset<right_bracket.size()){
size_t temp=repeat_out(k,_biggest_recursive_num,modify_place[k][p].max_len,new_offset);
k=right_bracket[new_offset][0]-1;
p=right_bracket[new_offset][1]+1;
new_offset+=temp;
repeat_leap=true;
goto break_re;
}else p=modify_place[k][p].max_len;
}
else p=modify_place[k][p].max_len;
break;
}
case 8:{
int t_t=get_random_number(static_cast<int>(modify_place[k][p].min_val),static_cast<int>(modify_place[k][p].max_val));
cout<<t_t;
p=modify_place[k][p].max_len;
break;
}
case 9:{
cout<<index;
p=modify_place[k][p].max_len;
break;
}
case 10:{
cout<<get_random_number(static_cast<uint64_t>(1e11),static_cast<uint64_t>(2e11-1));
p=modify_place[k][p].max_len;
break;
}
case 11:{
int major_length=get_random_number(5,14);
for(int i=0;i<major_length;i++)
cout<<email_char_list[get_random_number<int>(0,61)];
cout<<"@163.com";
p=modify_place[k][p].max_len;
break;
}
}
}
else {
if(content[k][p]=='\'') continue;
cout<<content[k][p];
if(content[k][p]==','&&!convert_) cout<<'\n',next_line=false;
}
}
if(next_line) cout<<'\n';
break_re:;
}
flag=false;
}
return increment;
}
public:
compiler()=default;
compiler(const compiler&)=delete;
compiler operator=(const compiler&)=delete;
void content_out()
{
bool repeat_leap=false;int p{},offset{0};
for(size_t k=0;k<content.size();k++){
bool next_line=true;bool convert_=false;
if(!repeat_leap) p=0;
repeat_leap=false;
for(;p<content[k].size();p++){
if(!convert_&&content[k][p]=='{') ++offset;
if(content[k][p]=='\'') convert_=!convert_;
if(p-1>=0&&(convert_&&((((content[k][p]=='{'&&content[k][p+1]=='{')||content[k][p]=='{'&&content[k][p-1]=='{'))||(((content[k][p]=='}'&&content[k][p+1]=='}')||content[k][p]=='}'&&content[k][p-1]=='}')))))
continue;
if(modify_place[k][p].order){
switch(modify_place[k][p].order){
case 1:{cout<<fixed<<setprecision(modify_place[k][p].max_out_floating)<<get_random_number<double>(modify_place[k][p].min_val,modify_place[k][p].max_val),p=modify_place[k][p].max_len;break;}
case 2:{
int t_t=get_random_number<int>(0,modify_place[k][p].rd_array.size()-1);
cout<<modify_place[k][p].rd_array[t_t];
p=modify_place[k][p].max_len;
break;
}
case 3:{
int t_t=get_random_number<int>(0,keywords[3].size()-1);
cout<<keywords[3][t_t];
p=modify_place[k][p].max_len;
break;
}
case 4:{
int t_t=get_random_number<int>(0,2);
cout<<keywords[4][t_t];
p=modify_place[k][p].max_len;
break;
}
case 5:{
int t_t=get_random_number<int>(0,keywords[5].size()-1);
cout<<keywords[5][t_t];
p=modify_place[k][p].max_len;
break;
}
case 6:{
int t_t=get_random_number<int>(0,keywords[6].size()-1);
cout<<keywords[6][t_t];
p=modify_place[k][p].max_len;
break;
}
case 7:{
int _biggest_recursive_num=get_random_number(static_cast<int>(modify_place[k][p].min_val),static_cast<int>(modify_place[k][p].max_val));
if(convert_) convert_=false;
if(_biggest_recursive_num>0){
if(offset<right_bracket.size()-1){
int num=repeat_out(k,_biggest_recursive_num,modify_place[k][p].max_len,offset);
k=right_bracket[offset][0]-1;
p=right_bracket[offset][1]+1;
offset+=num;
repeat_leap=true;
goto l;
}else p=modify_place[k][p].max_len;
}
else p=modify_place[k][p].max_len;
break;
}
case 8:{
int t_t=get_random_number(static_cast<int>(modify_place[k][p].min_val),static_cast<int>(modify_place[k][p].max_val));
cout<<t_t;
p=modify_place[k][p].max_len;
break;
}
case 10:{
cout<<get_random_number(static_cast<uint64_t>(1e11),static_cast<uint64_t>(2e11-1));
p=modify_place[k][p].max_len;
break;
}
case 11:{
int major_length=get_random_number(5,14);
for(int i=0;i<major_length;i++)
cout<<email_char_list[get_random_number<int>(0,61)];
cout<<"@163.com";
p=modify_place[k][p].max_len;
break;
}
}
}
else {
if(content[k][p]=='\'') continue;
cout<<content[k][p];
if(content[k][p]==','&&!convert_) cout<<'\n',next_line=false;
}
}
if(next_line) cout<<'\n';
l:;
}
}
void pre_search(){
stack<array<int,2>> compiler_guard;
int brucket_count=-1;
right_bracket.resize(1024);
bool instruction_mode=false;
for(int i=0;i<content.size();++i)
{
string &json_line=content[i];
for(int j=0;j<json_line.size();++j)
{
switch(json_line[j])
{
case '(':
{
if(instruction_mode) continue;
compiler_guard.push({json_line[j]});
break;
}
case ')':
{
if(instruction_mode) continue;
if(compiler_guard.empty()||(compiler_guard.top())[0]!='(') throw_mistake(i,"expected '('");
compiler_guard.pop();
break;
}
case '{':
{
if(!instruction_mode)
compiler_guard.push({json_line[j],++brucket_count});
break;
}
case '}':
{
if(!instruction_mode) {
if(compiler_guard.empty()||(compiler_guard.top())[0]!='{') throw_mistake(i,"expected '{'");
int pos=compiler_guard.top()[1];
if(pos>=right_bracket.size()) right_bracket.resize(pos*2);
right_bracket[pos]={i,j};
compiler_guard.pop();
}
break;
}
case '[':
{
if(instruction_mode) continue;
compiler_guard.push({json_line[j]});
break;
}
case ']':
{
if(instruction_mode) continue;
if(compiler_guard.empty()||(compiler_guard.top())[0]!='[') throw_mistake(i,"expected ']'");
compiler_guard.pop();
//right_bracket.push_back(i);
break;
}
case '\'':
{
instruction_mode=!instruction_mode;
break;
}
}
}
}
right_bracket.erase(right_bracket.begin()+brucket_count+1,right_bracket.end());
right_bracket.shrink_to_fit();
if(instruction_mode) throw_mistake(0,"expected ']'");
}
void keywords_prepare()
{
function<bool(const string&,const string&&)> judge=[&](const string& str1,const string& str2)
{
for(unsigned int i=0;i<str2.size();i++)
if(str1[i]!=str2[i]) return false;
return true;
};
bool instruction_mode=false;
for(size_t i=0;i<content.size();++i)
{
string &json_line=content[i];
bool ok=false;
for(size_t j=0;j<json_line.size();++j)
{
if(json_line[j]=='\'') instruction_mode=!instruction_mode;
if(instruction_mode==false) continue;
if(json_line[j]=='{'&&json_line[j-1]=='{') ok=true;
if(json_line[j]=='}'&&json_line[j-1]=='}') ok=false;
if(!ok) continue;
const string &&t=content[i].substr(j,16);
if(judge(t,"floating")){
auto [min_val,max_val,max_len,max_floating_point]=keyword_getvalue(json_line,j+8,i);
modify_place[i][j]={max_len,1,min_val,max_val,max_floating_point};
continue;
}
if(judge(t,"random"))
{
const auto &[vec,pos]=keyword_random(json_line,j,i);
attribute temp{pos,2};
temp.rd_array=vec;
modify_place[i][j]=temp;
continue;
}
if(judge(t,"city"))
{
size_t max_len=keyword_getlen(json_line,j+4,i);
modify_place[i][j]={max_len,3};
continue;
}
if(judge(t,"gender"))
{
size_t max_len=keyword_getlen(json_line,j+6,i);
modify_place[i][j]={max_len,4};
continue;
}
if(judge(t,"firstName"))
{
size_t max_len=keyword_getlen(json_line,j+9,i);
modify_place[i][j]={max_len,5};
continue;
}
if(judge(t,"surname"))
{
size_t max_len=keyword_getlen(json_line,j+7,i);
modify_place[i][j]={max_len,6};
continue;
}
if(judge(t,"repeat"))
{
auto [min_val,max_val,max_len,useless___]=keyword_getvalue(json_line,j+6,i);
modify_place[i][j]={max_len,7,min_val,max_val};
continue;
}
if(judge(t,"integer"))
{
auto [min_val,max_val,max_len,useless___]=keyword_getvalue(json_line,j+7,i);
modify_place[i][j]={max_len,8,min_val,max_val};
continue;
}
if(judge(t,"index"))
{
size_t max_len=keyword_getlen(json_line,j+5,i);
modify_place[i][j]={max_len,9};
continue;
}
if(judge(t,"phone"))
{
size_t max_len=keyword_getlen(json_line,j+5,i);
modify_place[i][j]={max_len,10};
continue;
}
if(judge(t,"email"))
{
size_t max_len=keyword_getlen(json_line,j+5,i);
modify_place[i][j]={max_len,11};
continue;
}
}
}
}
};
int compiler::left_bracket_num=0;
int main()
{
ios::sync_with_stdio(false);
cin.tie(nullptr),cout.tie(nullptr);
//freopen("example.txt","r",stdin);
freopen("test.txt","w",stdout);
string t;
init();
content.reserve(1024);
while(getline(cin,t),t[0]!='\0') content.emplace_back(t);
compiler x;
x.pre_search();
x.keywords_prepare();
x.content_out();
}
08-29
2734
![](https://csdnimg.cn/release/blogv2/dist/pc/img/readCountWhite.png)
09-03
371
![](https://csdnimg.cn/release/blogv2/dist/pc/img/readCountWhite.png)
08-31
1860
![](https://csdnimg.cn/release/blogv2/dist/pc/img/readCountWhite.png)
08-29
473
![](https://csdnimg.cn/release/blogv2/dist/pc/img/readCountWhite.png)