% Konverzia medzi nazvami a vzorcami chemickych zlucenin % Zapoctovy program z predmetu Neproceduralne programovanie % Radoslav Glinsky % 2009 % formula_to_name(+Vzorec,-Meno) - pomenuje zluceninu Vzorec formula_to_name(Formula,Name):- analyze_formula(Formula,Name). % name_to_formula(+Meno,-Vzorec) - prevedie meno na vzorec name_to_formula(Name,Formula):- analyze_name(Name,Formula). %%% Analyza a prevod vzorca na meno %% Blok vsetkych analyzacnych procedur na urcenia mena zo vzorca %% analyze_formula(+Formula,-Name) - zisti o aku zluceninu sa jedna a pomenuje ju analyze_formula('H2O','voda'):- !. % trivialne nazvy analyze_formula('NH3','amoniak'):- !. analyze_formula('O3','ozon'):- !. analyze_formula('H2S','sulfan'):- !. analyze_formula(Formula,Name):- reg_match('[A..Z]$',Formula), element(Name,_,Formula,_), !. analyze_formula(Formula,Name):- reg_match('[A..Z][a..z]$',Formula), element(Name,_,Formula,_), !. analyze_formula(Formula,Name):- reg_match('["H","N","O","I","Br","F","Cl"]2$',Formula), name(Formula,List), cut_element(List,Out), name(Element,Out), element(Name,_,Element,_), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]H$',Formula), % hydridy name_hydride(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]H{1,2}[0..9]$',Formula), name_hydride(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]{0,2}[0..9]O$',Formula), % oxidy name_oxide(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]{0,2}[0..9]O{1,2}[0..9]$',Formula), name_oxide(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]OH',Formula), % hydroxidy name_hydroxide(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z](OH){1,2}[0..9]',Formula), name_hydroxide(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('H["Cl","F","I","Br"]$',Formula), % halogenove kyseliny name_halogen_acid(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]{0,2}[0..9]["Cl","F","Br","I"]$',Formula), % analyza soli hal. kys. name_halogenid(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('[A..Z]{0,1}[a..z]{0,2}[0..9]["Cl","F","Br","I"]{0,2}[0..9]$',Formula), name_halogenid(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('H[A..Z]{0,1}[a..z]O$',Formula), % analyza oxokyselin name_ox_acid(Formula,Name), !. analyze_formula(Formula,Name):- reg_match('H{0,2}[0..9][A..Z]{0,1}[a..z]{0,2}[0..9]O{1,2}[0..9]$',Formula), name_ox_acid(Formula,Name), !. %% koniec bloku a analyzacnymi procedurami na prev zo vzorca na meno %% analyze trvialnych nazvov % cut_element(+List,-Out) - vysekne len kody prveho alebo prvych dvoch pismen cut_element([U,L,N],[U,L]):- digit(N), upper(U), lower(L). cut_element([U,N],[U]):- digit(N), upper(U). %%% koniec analyzy trivialnych pripadov %%% analyza hydridov % name_hydride(+Formula,-Name) % pomenuje hydrid name_hydride(Formula,Name):- name(Formula,List), hydride_cation(List,Cation,Rest), hydride_anion(Rest,Multi), num_suffix(Multi,Suffix), element(_,Base,Cation,OxList), member(Multi,OxList), concatenate(['hydrid',' ',Base,Suffix,'y'],Name). % hydride_cation(+List,-Sign,-Rest) - zisti znacku cationu a vrati zbytok zoznamu hydride_cation([U,L|T],Cation,T):- upper(U), lower(L), name(Cation,[U,L]), !. hydride_cation([U1,U2|T],Cation,[U2|T]):- upper(U1), upper(U2), name(Cation,[U1]), !. % hydride_anion(+List,-Multi) - vrati nasobnost hydridoveho anionu hydride_anion([Hydrogen],1):- name('H',[Hydrogen]), !. hydride_anion([Hydrogen,Num],Multi):- digit(Num), name('H',[Hydrogen]), name(Multi,[Num]), !. hydride_anion([Hydrogen,N1,N2],Multi):- digit(N1), digit(N2), name('H',[Hydrogen]), name(Multi,[N1,N2]), !. %%% koniec analyzy hydridov %% analyza oxidov %% name_oxide(+Vzorec,-Meno) - procedura pomenuvajuca oxidy name_oxide(Formula,Name):- name(Formula,List), oxide_cation(List,CMulti,Sign,Rest), oxide_anion(Rest,AMulti), Num is 2*AMulti/CMulti, element(_,Base,Sign,_), (suffix_exception(Sign,Num,Suffix); num_suffix(Num,Suffix)), concatenate(['oxid',' ',Base,Suffix,'y'],Name), !. % oxide_cation(+List,-CMulti,-Sign,-Zbytok) - vyberie kation a urci jeho nasobnost oxide_cation(List,Num,Sign,Rest2):- get_oxide_cation(List,Sign,Rest1), oxide_cation_num(Rest1,Num,Rest2). % get_oxide_cation(+In,-Znacka,-Zbytok) - vybeie kation a prevedie na retazec get_oxide_cation([U,X|T],Sign,[X|T]):- upper(U), \+lower(X), name(Sign,[U]). get_oxide_cation([U,L|T],Sign,T):- upper(U), lower(L), name(Sign,[U,L]). % oxide_cation_num(+List,-Num,-Zbytok) - vyberie nasobnost kationu oxide_cation_num([Oxygen|T],1,[Oxygen|T]):- name('O',[Oxygen]). oxide_cation_num([N,X|T],Num,[X|T]):- digit(N), \+digit(X), name(Num,[N]). oxide_cation_num([N1,N2|T],Num,T):- digit(N1), digit(N2), name(Num,[N1,N2]). % oxide_anion(+List,-Nasobnost) - vyberie nasobnost oxidoveho anionu oxide_anion([Oxygen],1):- name('O',[Oxygen]). oxide_anion([Oxygen,N],Num):- name('O',[Oxygen]), name(Num,[N]). oxide_anion([Oxygen,N1,N2],Num):- name('O',[Oxygen]), name(Num,[N1,N2]). %% koniec analyzy oxidov %% analyza hydroxidov % name_hydroxide(+Formula,-Name) - pomenuje vzorec hydroxidu name_hydroxide(Formula,Name):- name(Formula,List), hydroxide_cation(List,Sign,Rest), hydroxide_anion(Rest,Multi), element(_,Base,Sign,OxList), num_suffix(Multi,Suffix), member(Multi,OxList), concatenate(['hydroxid',' ',Base,Suffix,'y'],Name), !. % hydroxide_cation(+List,-Sign,-Zbytok) - vyberie kation hydroxide_cation([U,L|T],Sign,T):- upper(U), lower(L), name(Sign,[U,L]). hydroxide_cation([U,X|T],Sign,[X|T]):- upper(U), \+lower(X), name(Sign,[U]). % hydroxide_anion(+List,-Nasobnost) - vyberie nasobnost hydroxidoveho anionu hydroxide_anion([O,H],1):- name('OH',[O,H]). hydroxide_anion([L,O,H,R,N],Num):- left_bracket(L), right_bracket(R), name('OH',[O,H]), digit(N), name(Num,[N]). hydroxide_anion([L,O,H,R,N1,N2],Num):- left_bracket(L), right_bracket(R), name('OH',[O,H]), digit(N1), digit(N2), name(Num,[N1,N2]). %% koniec analyzy hydroxidov %% analyza halogenovych kyselin % name_halogen_acid(+Formula,-Name) - pomenuje halogenovu kyselinu name_halogen_acid(Formula,Name):- name(Formula,List), get_halogen_acid(List,Sign), element(_,Base,Sign,_), concatenate(['kyselina',' ',Base,'o','vodikova'],Name), !. % get_halogen_acid(+List,-Sign) - vrati znacku halogenoveho prvku z nazvu get_halogen_acid([H,U],Sign):- upper(U), name('H',[H]), name(Sign,[U]). get_halogen_acid([H,U,L],Sign):- upper(U), lower(L), name('H',[H]), name(Sign,[U,L]). %% koniec analyzy halogenovych kyselin %% analyza soli halogenovych kyselin % name_halogenid(+Formula,-Name) - pomenuje halogenid name_halogenid(Formula,Name):- name(Formula,List), halogen_cation(List,CSign,Rest), halogen_cation_num(Rest,CMulti,Rest2), halogen_anion(Rest2,AMulti,ASign), halogenid(CSign,CMulti,ASign,AMulti,Name), !. % halogen_cation(+List,-Sign,-Rest) - vrati znacku kationu a zvysok zoznamu halogen_cation([U,L|T],Sign,T):- upper(U), lower(L), name(Sign,[U,L]). halogen_cation([U,X|T],Sign,[X|T]):- upper(U), \+lower(X), name(Sign,[U]). % halogen_cation_num(+List,-Num,-Rest) - vrati pocetnost kationu a zbytok halogen_cation_num([X|T],1,[X|T]):- \+digit(X). halogen_cation_num([N,X|T],Num,[X|T]):- digit(N), \+digit(X), name(Num,[N]). halogen_cation_num([N1,N2|T],Num,T):- digit(N1), digit(N2), name(Num,[N1,N2]). % halogen_anion(+List,-Num,-Sign) - vrati pocetnost a znacku halogenu halogen_anion([U,L],1,Sign):- upper(U), lower(L), name(Sign,[U,L]). halogen_anion([U],1,Sign):- upper(U), name(Sign,[U]). halogen_anion([U,L,N],Num,Sign):- upper(U), lower(L), digit(N), name(Num,[N]), name(Sign,[U,L]). halogen_anion([U,L,N1,N2],Num,Sign):- upper(U), lower(L), digit(N1), digit(N2), name(Num,[N1,N2]), name(Sign,[U,L]). halogen_anion([U,N],Num,Sign):- upper(U), digit(N), name(Num,[N]), name(Sign,[U]). halogen_anion([U,N1,N2],Num,Sign):- upper(U), digit(N1), digit(N2), name(Num,[N1,N2]), name(Sign,[U]). % halogenid(+Sign1,+Multi1,+Sign2,+Multi2,Name) - najde spravne koncovky a pospaja do nazvu halogenid(Sign1,Multi1,Sign2,Multi2,Name):- Num is Multi2 / Multi1, element(_,CBase,Sign1,_), element(_,ABase,Sign2,_), num_prefix(Multi1,Prefix), (suffix_exception(Sign1,Num,Suffix); num_suffix(Num,Suffix)), concatenate([ABase,'id',' ',Prefix,CBase,Suffix,'y'],Name). %% koniec analyzy soli halogenovych kyselin %% analyza kyslikatych kyselin % name_ox_acid(+Formula,-Name) - pomenuje kyslikatu kyselinu name_ox_acid(Formula,Name):- name(Formula,List), acid_hydrogen_num(List,HNum,Rest), acid_element(Rest,Element,Rest2), acid_element_num(Rest2,ENum,Rest3), acid_oxygen_num(Rest3,ONum), element(_,Base,Element,_), Num is ((2*ONum) - HNum)/ENum, (suffix_exception(Element,Num,Suffix); num_suffix(Num,Suffix)), concatenate(['kyselina',' ',Base,Suffix,'a'],Name), !. % acid_hydrogen_num(+List,-HNum,-Rest) - vrati pocet vodikov a zbytok vzorca acid_hydrogen_num([H,U|T],1,[U|T]):- name('H',[H]), upper(U), !. acid_hydrogen_num([H,N,U|T],Num,[U|T]):- name('H',[H]), digit(N), upper(U), name(Num,[N]), !. acid_hydrogen_num([H,N1,N2,U|T],Num,[U|T]):- name('H',[H]), digit(N1), digit(N2), upper(U), name(Num,[N1,N2]), !. % acid_element(+List,-Element,-Rest) - vrati znak prvku a cislo a zbytok acid_element([U,X|T],E,[X|T]):- upper(U), \+lower(X), name(E,[U]), !. acid_element([U,L,X|T],E,[X|T]):- upper(U), lower(L), \+lower(X) ,name(E,[U,L]), !. % acid_element_num(+List,-ENum,-Rest) - vrati pocty kyselinotvornych prvkov acid_element_num([O|T],1,[O|T]):- name('O',[O]), !. acid_element_num([N,O|T],Num,[O|T]):- digit(N), name('O',[O]), name(Num,[N]), !. acid_element_num([N1,N2,O|T],Num,[O|T]):- digit(N1), digit(N2), name('O',[O]), name(Num,[N1,N2]), !. % acid_oxygen_num(+List,-ONum) - vrati pocet kyslikov v kyseline acid_oxygen_num([O],1):- name('O',[O]). acid_oxygen_num([O,N],Num):- digit(N), name('O',[O]), name(Num,[N]), !. acid_oxygen_num([O,N1,N2],Num):- digit(N1), digit(N2), name('O',[O]), name(Num,[N1,N2]), !. %% koniec analyzy kyslikatych kyselin %%% Koniec bloku prevodu mena na vzorec %%% Prevod z mena na vzorec %% matchovanie nazvu a priradenie spravnej procedury %% Blok analyzacnych procedur na prevod medzi menom a vzorcom % analyze_name(+Meno,-Vzorec) - prevedie meno na vzorec analyze_name('voda','H2O'):- !. analyze_name('cpavok','NH3'):- !. analyze_name('ozon','O3'):- !. analyze_name('kyselina sulfonova','H2S'):- !. analyze_name('kyselina sirovodikova','H2S'):- !. analyze_name(Name,Formula):- element(Name,_,Formula,_), !. analyze_name(Name,Formula):- reg_match('hydrid *',Name), formulize_hydride(Name,Formula), !. analyze_name(Name,Formula):- reg_match('oxid *',Name), formulize_oxide(Name,Formula), !. analyze_name(Name,Formula):- reg_match('hydroxid *',Name), formulize_hydroxide(Name,Formula), !. analyze_name(Name,Formula):- reg_match('["chlor","brom","jod","fluor"]id *',Name), formulize_halogenide(Name,Formula), !. analyze_name(Name,Formula):- reg_match('kyselina *vodikova$',Name), formulize_halogen_acid(Name,Formula), !. analyze_name(Name,Formula):- reg_match('kyselina *a',Name), formulize_ox_acid(Name,Formula), !. %% Koniec bloku analyzacnych procedur %% Blok definicii pomocnych procedur pre prevod z mena na vzorec %% analyza hydridov % formulize_hydride(+Name,-Formula) - prevedie hydrid na vzorec formulize_hydride(Name,Formula):- cut_suffix('y',Name,Rest), cut_prefix('hydrid ',Rest,Rest2), cut_ox_suffix(Rest2,_,Num,Base), element(_,Base,Sign,OxList), member(Num,OxList), number_one(Num,OutNum), concatenate([Sign,'H',OutNum],Formula), !. %% koniec analyzy hydridov %% analyza oxidov % formulize_oxide(+Name,-Formula) - prevedie oxid na vzorec formulize_oxide(Name,Formula):- cut_suffix('y',Name,Rest), cut_prefix('oxid ',Rest,Rest2), cut_ox_suffix(Rest2,_,Num,Base), element(_,Base,Sign,_), oxide_numbers(Num,1,ENum,ONum), number_one(ENum,SENum), number_one(ONum,SONum), concatenate([Sign,SENum,'O',SONum],Formula), !. % oxide_numbers(+Num,+ENum,-ENum,-ONum) - vrati pocty atomov prvku a kysliku oxide_numbers(Num,ENum,ENum,ONum):- ONum is (ENum*Num/2), is_natural(ONum), !. oxide_numbers(Num,ENum,ENum3,ONum3):- ONum is (ENum*Num/2), \+is_natural(ONum), ENum2 is 2*ENum, oxide_numbers(Num,ENum2,ENum3,ONum3), !. %% koniec analyzy oxidov %% analyza hydroxidov % formulize_hydroxide(+Name,-Formula) - prevedie hydroxid na vzorec formulize_hydroxide(Name,Formula):- cut_suffix('y',Name,Rest), cut_prefix('hydroxid ',Rest,Rest2), cut_ox_suffix(Rest2,_,Num,Base), element(_,Base,Sign,OxList), member(Num,OxList), number_one(Num,ONum), num_brackets(Num,L,R), concatenate([Sign,L,'OH',R,ONum],Formula), !. %% koniec analyzy hydroxidov %% analyza halogenovych kyselin % formulize_halogen_acid(+Name,-Formula) - prevedie halogenovu kyselinu na vzorec formulize_halogen_acid(Name,Formula):- cut_prefix('kyselina ',Name,Rest), cut_suffix('ovodikova',Rest,Base), element(_,Base,Sign,_), concatenate(['H',Sign],Formula), !. %% koniec analyzy halogenovych kyselin %% analyza halogenidov % formulize_halogenide(+Name,-Formula) - prevedie sol halogenovej kyseliny na vzorec formulize_halogenide(Name,Formula):- halogen_prefix(Name,HSign,Rest), cut_suffix('y',Rest,Rest2), cut_ox_suffix(Rest2,_,Num,CBase), element(_,CBase,CSign,OxList), member(Num,OxList), number_one(Num,ONum), concatenate([CSign,HSign,ONum],Formula), !. % halogen_prefix(+Name,-HSign,-Rest) - vysekne z nazvu halogenid a vrati jeho znacku halogen_prefix(Name,HSign,Rest):- cut_in_space(Name,HPart,Rest), cut_suffix('id',HPart,Base), element(_,Base,HSign,_), !. %% koniec analyzy halogenidov %% analyza kyslikatych kyselin % formulize_ox_acid(+Name,-Formula) - prevedie kyslikatu kyselinu na vzorec formulize_ox_acid(Name,Formula):- cut_prefix('kyselina ',Name,Rest), cut_suffix('a',Rest,Rest2), cut_ox_suffix(Rest2,_,ENum,Base), element(_,Base,Sign,OxList), member(ENum,OxList), find_hydro_ox(ENum,1,1,HNum,ONum), number_one(HNum,HNum2), number_one(ONum,ONum2), concatenate(['H',HNum2,Sign,'O',ONum2],Formula), !. % find_hydro_ox(+ENum,+HNum,+ONum,-OutHNum,-OutONum) - zisti pocet vodikov a kyslikov find_hydro_ox(ENum,HNum,ONum,HNum,ONum):- 0 is (HNum + ENum - 2*ONum), !. find_hydro_ox(ENum,HNum,ONum,OutHNum,OutONum):- N is (HNum + ENum - 2*ONum), N < 0, HNum =< 20, ONum =< 10, HNum1 is HNum + 1, find_hydro_ox(ENum,HNum1,ONum,OutHNum,OutONum). find_hydro_ox(ENum,HNum,ONum,OutHNum,OutONum):- N is (HNum + ENum - 2*ONum), N > 0, HNum =< 20, ONum =< 10, ONum1 is ONum + 1, find_hydro_ox(ENum,HNum,ONum1,OutHNum,OutONum). %% koniec analyzy kyslikatych kyselin %%% Koniec prevodu mena na vzorec %%% spajanie retazcov a analyza znakov a pomocne procedury % cut_in_space(+String,-String1,-String2) - rozdeli string v medzere a vrati prvu a druhu cast cut_in_space(String,Part1,Part2):- name(String,SList), list_cut_space(SList,PL1,PL2), name(Part1,PL1), name(Part2,PL2). % list_cut_space(+List,-PList1,-PList2) - rozdeli list na znaku ' ' = 32 list_cut_space([32|T],[],T):- !. list_cut_space([X|T],[X|Out1],Out2):- \+space(X), list_cut_space(T,Out1,Out2). % num_brackets(+Num,-L,-R) - ak je cislo 1 budu retazce L a R prazdne, inak zatvorky num_brackets(1,'',''). num_brackets(N,'(',')'):- N > 1. % number_one(+In,-Out) - ak je vzstup jednicka, vrati prazdny retazec, ak je vacsi, vrati vstup number_one(1,''):- !. number_one(N,N):- N > 1, !. % is_natural(+N) - zisti, ci je cislo prirodzene is_natural(1). is_natural(N):- N > 0, N1 is N - 1, is_natural(N1). % %concatenate(+ListOfString,Name) - pospaja zoznam stringov do jedneho concatenate(StrList,Name):- strlist_to_list(StrList,List), name(Name,List). % strlist_to_list(+In,-Out) - zo zoznam retazcov premeni na zoznam cislenych hodnot a pospaja strlist_to_list([],[]). strlist_to_list([H|T],Out):- name(H,List), strlist_to_list(T,R), append(List,R,Out). left_bracket(X):- X == 40. % zisti, ci je vstupny kod lava zatvorka right_bracket(X):- X == 41. % zisti, ci je vstupny kod prava zatvorka digit(X):- % zisti, ci je vstupny kod cislica X >= 48, X =<58. upper(X):- % ci je kod kodom velkych pismen X >= 65, X =< 90. lower(X):- % ci je vstupny kod vstupom malych pismen X >= 97, X =< 122. space(X):- X == 32. %%% koniec spajania retazcov a znakovych funkcii %%% Definicia regularnych vyrazov a pomocnych funkcii na spracovanie %% pomocne funkcie na spracovanie nazvu % cut_prefix(+Prefix,+String,-RestString) - vysekne predponu a vrati zbytok cut_prefix(Prefix,String,RestString):- name(Prefix,PrefixList), name(String,StringList), prefix(PrefixList,StringList,RestList), name(RestString,RestList), !. % cut_suffix(+Suffix,+String,-RestString) - vysekne priponu a vrati zbytok cut_suffix(Suffix,String,RestString):- name(Suffix,SuffixList), name(String,StringList), suffix(SuffixList,StringList,RestList), name(RestString,RestList), !. % cut_ox_suffix(+String,-Suffix,-Num,-Rest) - vrati oxidacne cislo, koncovku a zbytok cut_ox_suffix(String,Suffix,Num,Rest):- num_suffix(Num,Suffix), cut_suffix(Suffix,String,Rest), !. %% koniec definicie pomocnych funkcii na spracovanie % reg_match(+RegExp,+String) - analyza retazca porovnanim pomocou regularneho vyrazu reg_match(RegExp,String):- name(RegExp,RList), name(String,SList), regexp(RList,SList). regexp([],_):- !. % prazdny matchuje na vsetko regexp([36],[]):- !. % koniec riadku '$' regexp([42],_):- !. regexp([46|RT],[_|ST]):- regexp(RT,ST), !. % jeden lubovolny prvok '.' regexp([42|RT],[SH|ST]):- regexp(RT,[SH|ST]). % riesi '*' lubovolny pocet lubovolnych znakov regexp([42|RT],[_|ST]):- regexp([42|RT],ST). % '*' lubovolny pocet lubovolnych znakov regexp([91|RT],[SH|ST]):- analyze_list([91|RT],[SH|ST]), !. % pusti procedury na zoznam matchov regexp([123|RT],[SH|ST]):- analyze_multiples([123|RT],[SH|ST]), !. % riesenie nasobnosti '{a,b}' regexp([RH|RT],[SH|ST]):- RH == SH, regexp(RT,ST). % analyze_list(+RegExp,+List) - vyhodnoti zoznam a na zvysok pusti proceduru regexp analyze_list(RegIn,ListIn):- cut_list(RegIn,Interior,RegRest), analyze_interior(Interior,ListIn,ListRest), regexp(RegRest,ListRest). % cut_list(+RegExp,-Interior,-Rest) vystrihne cast so zoznamom, vrati vnutro a zbytok cut_list([91|RT],Interior,RegRest):- cut_list(RT,Interior,RegRest). % lava zatvorka cut_list([93|RT],[],RT). % prava zatvorka cut_list([RH|RT],[RH|Interior],RegRest):- RH \= 91, RH \=93, cut_list(RT,Interior,RegRest). % analyzuje vnutro zoznamu a podla obsahu spusti prislusnu proceduru analyze_interior([B,46,46,E],[LH|LT],LT):- LH >= B, LH =< E, !. % riesi intervalovy zoznam analyze_interior(Interior,InList,ListRest):- listize(Interior,'i',Patterns), match_patterns(Patterns,InList,ListRest). % listize(+In,+Sign,-Out) - premeni zoznam hodnot v "" na zoznam zoznamov listize([34],'o',[[]]). % 'o' znaci vystupne ", riesi koniec zoznamu listize([34|T],'i',Out):- listize(T,'o',Out), !. % riesi vstupne " 'i' a pusti listize znova s 'o' listize([34|T],'o',Out):- listize(T,'i',Out), !. % riesi vystupne '"' listize([44|T],'i',[[]|Out]):- listize(T,'i',Out), !. % riesi ciarky medzi vzormi listize([H|T],'o',[[H|TH]|TT]):- H \= 34, H \= 44, listize(T,'o',[TH|TT]). % riesi vkladanie v zoznamoch % match_patterns(+Patterns,+InList,-ListRest) - vybera vzory zo zoznamu a skusa napasovat, vrati zbytok match_patterns([PH|_],InList,ListRest):- prefix(PH,InList,ListRest), !. % ak pasuje prvy prvok match_patterns([_|PT],InList,ListRest):- match_patterns(PT,InList,ListRest). % postup dalej % suffix(+Suffix,+InList,-ListRest) - zisti, ci je koncovou a vrati zbytok ak ano suffix(S,List,Rest):- reverse(S,RS), reverse(List,RL), prefix(RS,RL,RR), reverse(RR,Rest), !. % prefix(+Pattern,+InList,-ListRest) - zisti, ci je Pattern predponou InList a zvysok vrati v ListRest prefix([],List,List). prefix([PH|PT],[LH|LT],List):- PH == LH, prefix(PT,LT,List). % analyze_multiples(+RegExp,+List) - zisti nasobky a skusi napasovat na vyraz za nasobkami analyze_multiples([123,BN,44,EN,125|RT],List):- get_exp(RT,NRE,Rest), name(B,[BN]), name(E,[EN]), match_multi(NRE,Rest,B,E,List). % get_exp(+RegExp,-Vyraz,-Zbytok) - vysekne prvy vyraz ako celok get_exp([H|T],[H],T):- H \= 91, H \= 93, H \= 123, H \= 125. get_exp([91|T],Out,Rest):- get_interval([91|T],Out,Rest). % get_interval(+RegExp,-Inteval,-Rest) - vysekne z regexpu interval zo zaciatku get_interval([91|RT],[91|Out],Rest):- get_interval(RT,Out,Rest). % zaciatok intervalu get_interval([H|T],[H|Out],Rest):- H \= 91, H \= 93, get_interval(T,Out,Rest). % prvok vo vnutri get_interval([93|T],[93],T). % match_multi(+RPart,RegExp,+Min,+Akt,List) - ak je akt>=min prida do regexp rpart a skusi vyhodnotit match_multi(RPart,RegExp,Min,Min,List):- Min >= 0, multi_append(RPart,RegExp,Min,MultiRegExp), regexp(MultiRegExp,List), !. match_multi(RPart,RegExp,Min,Akt,List):- Akt > Min, Min >=0, multi_append(RPart,RegExp,Akt,OutRegExp), regexp(OutRegExp,List). match_multi(RPart,RegExp,Min,Akt,List):- Akt > Min, Akt1 is Akt - 1, match_multi(RPart,RegExp,Min,Akt1,List), !. % multi_append(+Vzorka,+RegExp,+Pocet,-MultiVyraz) - vrati pocetkrat zoznam s pocetkrat pridanou vzorkou multi_append(_,RegExp,0,RegExp):- !. multi_append(RPart,RegExp,N,Out):- N > 0, M is N - 1, multi_append(RPart,RegExp,M,Result), append(RPart,Result,Out). %%% Koniec definicie regularnych vyrazov a pomocnych funkcii na spracovanie %% tabulka prvkov, tabulka cisloviek, predpon a pripon % num_prefix(?Cislo,?Predpona) - zisti latinsky nazov cisovky num_prefix(0,''). num_prefix(1,''). num_prefix(1,'mono'). num_prefix(2,'di'). num_prefix(3,'tri'). num_prefix(4,'tetra'). num_prefix(5,'penta'). num_prefix(6,'hexa'). num_prefix(7,'hepta'). num_prefix(8,'okna'). num_prefix(9,'nona'). num_prefix(10,'deka'). num_prefix(11,'undeka'). num_prefix(12,'dodeka'). % num_suffix(?Cislo,?Koncovka) - urcovanie koncoviek podla cisla num_suffix(5,'icn'). num_suffix(5,'ecn'). num_suffix(1,'n'). num_suffix(2,'nat'). num_suffix(4,'icit'). num_suffix(3,'it'). num_suffix(6,'ov'). num_suffix(7,'ist'). num_suffix(8,'icel'). num_suffix(6,''). % suffix_exception(+Znacka,+Cislo,-Koncovka) - databaza prvkov, kotre maju koncovku -ecny suffix_exception('Cl',5,'ecn'). suffix_exception('P',5,'ecn'). suffix_exception('F',5,'ecn'). % element(?Nazov,?SlovnyZaklad,?Znacka,?OxidacneCisla) - periodicka tabulka prvkov element('vodik','hydrogen','H',[-1,1]). % prva perioda element('helium','hel','He',1,[0]). element('litium','lit','Li',[1]). % druha perioda element('berylium','beryl','Be',[2]). element('bor','bor','B',[-3,3]). element('uhlik','uhol','C',[-4,2]). element('uhlik','uhl','C',[4]). element('dusik','dus','N',[-3,2,3,4,5]). element('kyslik','kysel','O',[-2]). element('fluor','fluor','F',[-1]). element('neon','neon','Ne',[0]). element('sodik','sod','Na',[1]). % tretia perioda element('horcik','horec','Mg',[2]). element('hlinik','hlin','Al',[3]). element('kremik','krem','Si',[-4,4]). element('fosfor','fosfor','P',[-3,1,3,5]). element('sira','sir','S',[-2,4,6]). element('chlor','chlor','Cl',[-1,1,5,7]). element('argon','argon','Ar',[0]). element('draslik','drasel','K',[1]). % stvrta perioda element('vapnik','vape','Ca',[2]). element('skandium','skand','Sc',[3]). element('titan','titan','Ti',[3,4]). element('vanad','vanad','V',[3,4,5]). element('chrom','chrom','Cr',[2,3,6]). element('mangan','mangan','Mn',[2,4,7]). element('zelezo','zelez','Fe',[2,3]). element('kobalt','kobalt','Co',[2,3]). element('nikel','nikel','Ni',[2]). element('nikel','nikl','Ni',[3]). element('med','med','Cu',[1,2]). element('zinok','zinoc','Zn',[2]). element('galium','gal','Ga',[3]). element('germanium','germa','Ge',[2]). element('germanium','german','Ge',[4]). element('arzen','arsen','As',[-3,3,5]). element('selen','selen','Se',[-2,4,6]). element('brom','brom','Br',[-1,1,5]). element('krypton','krypton','Kr',[0,4]). element('rubidium','rubid','Rb',[1]). % piata perioda element('stroncium','stronc','Sr',[2]). element('ytrium','ytr','Y',[3]). element('zirkon','zirkon','Zr',[3,5]). element('molybden','molybden','Mo',[4,6]). element('technecium','technec','Tc',[4,6]). element('ruthenium','ruthen','Ru',[3,4,8]). element('rhodium','rhod','Rh',[3,4]). element('paladium','palad','Pd',[2,4]). element('striebro','striebor','Ag',[1]). element('kadmium','kadem','Cd',[2]). element('indium','ind','In',[3]). element('cin','cin','Sn',[2,4]). element('antimon','antimon','Sb',[3,5]). element('telur','telur','Te',[-2,4,6]). element('jod','jod','I',[-1,1,5,7]). element('xenon','xenon','Xe',[0,4,6]). element('cezium','cez','Cs',[1]). % siesta perioda element('barium','bar','Ba',[2]). element('lantan','lantan','La',[3]). element('cer','cer','Ce',[3]). element('praseodym','praseodym','Pr',[3]). element('neodym','neodym','Nd',[3]). element('prometheum','prometh','Pm',[3]). element('samarium','samar','Sm',[3]). element('europium','europ','Eu',[3]). element('gadolinium','gadol','Gd',[3]). element('terbium','terb','Tb',[3]). element('dysprozium','dysproz','Dy',[3]). element('holmium','holm','Ho',[3]). element('erbium','erb','Er',[3]). element('thulium','thul','Tm',[3]). element('yterbium','yterb','Yb',[3]). element('lutecium','lutec','Lu',[3]). element('hafnium','hafn','Hf',[4]). element('tantal','tantal','Ta',[5]). element('wolfram','wolfram','W',[6]). element('rhenium','rhen','Re',[4,7]). element('osmium','osm','Os',[3,4,8]). element('iridium','irid','Ir',[3,4]). element('iridium','iridi','Ir',[6]). element('platina','plat','Pt',[2,4]). element('zlato','zlat','Au',[3]). element('ortut','ortut','Hg',[1,2]). element('thalium','thal','Tl',[1,3]). element('olovo','olov','Pb',[2,4]). element('bizmut','bizmut','Bi',[3]). element('polonium','polon','Po',[4]). element('astat','','At',[]). element('radon','','Rn',[0]). element('francium','franc','Fr',[1]). % siedma perioda element('radium','rad','Ra',[2]). element('aktinium','aktin','Ac',[3]). element('thorium','thori','Th',[6]). element('protaktinum','protaktin','Pa',[5]). element('uran','uran','U',[4]). element('neptunium','neptun','Np',[3,4]). element('plutonium','pluton','Pu',[4]). element('americium','americ','Am',[2,3,4]). element('curium','cur','Cm',[3]). element('berkelium','berkel','Bk',[3]). element('kalifornium','kaliforn','Cf',[3]). element('einsteinium','einstein','Es',[3]). element('fermium','ferm','Fm',[3]). element('mendelevium','mendelev','Md',[3]). element('nobelium','nobel','No',[3]). element('lawrencium','lawrenc','Lr',[3]). element('rutherfordium','rutherford','Rf',[4]). element('durbium','','Db',[]). element('seaborgium','','Sg',[]). element('bohrium','','Bh',[]). element('hassium','','Hs',[]). element('meitnerium','','Mt',[]).