:- module( device_medical, [ dev_set/2, dev_get/2, dev_do/2, %dev_query/2, dev_query/3, %DH 2003-03-21 valid_parameter/1 ] ). :- use_module( library(lists), [ member/2, select/3 ] ). :- use_module( library(system), [ datime/1 ] ). :- use_module( library(charsio), [ format_to_chars/3 ] ). :- use_module( library(oaag),[solve/1]). :- dynamic variable_value/2. %do solve here, so oaa setup message doesnt show up in middle of dialogue :- solve(disease_names(_));error:error('Can not find OAA device'). %%% Actions (action(+Name,+Parameters)) action( 'dummy', [parameter1] ). %action( 'TakeTest', [best_labtest] ). % This is needed if the device should be able to answer queries that resolve %issues that depend on other issues. Not needed in this domain, but needed in %e.g. telvcr. It is not pretty and it is not UPnP but I am not proposing %some kind of extended UPnP... - DH 21/3-2003 %%% query(+Query, +Parameters) query(X^bestq(X),[]). %%% Variable default values default_value( bla, hey ). %special_purpose dev_query (DH) dev_query(confirmed_by_interview,Com,confirmed_by_interview):- member(disease(D),Com), oaag:solve(description(D,disease(D,_,_,symptoms(S),_,history(H),_,_))), \+ ( member(symptom(S1,required(yes),_),S), \+member(symptom(S1),Com) ), \+ ( member(medicalHistory(H1,required(yes),_),H), \+member(medicalHistory(H1),Com) ),!. dev_query(confirmed_by_interview,Com,not(confirmed_by_interview)):- member(disease(D),Com), oaag:solve(description(D,disease(D,_,_,symptoms(S),_,history(H),_,_))), ( ( member(symptom(S1,required(yes),_),S), member(not(symptom(S1)),Com) ); ( member(medicalHistory(H1,required(yes),_),H), member(not(medicalHistory(H1)),Com) ) ),!. %dev_query(confirmed_by_interview,_Com,not(confirmed_by_interview)). dev_query(confirmed_by_interview,_Com,fail(confirmed_by_interview)). dev_query(confirmed_by_tests,Com,confirmed_by_tests):- member(disease(D),Com), oaag:solve(description(D,disease(D,_,_,_,tests(T),_,_,_))), \+ ( member(diagnosticTest(T1,_,_,required(yes),_),T), \+ member(test_result(T1),Com) ),!. dev_query(confirmed_by_tests,Com,not(confirmed_by_tests)):- member(disease(D),Com), oaag:solve(description(D,disease(D,_,_,_,tests(T),_,_,_))), member(diagnosticTest(T1,_,_,required(yes),_),T), member(not(test_result(T1)),Com ),!. dev_query(confirmed_by_tests,_Com,fail(confirmed_by_tests)). dev_query(X^info(X),Com,info(X)):- ( member(info_disease(D),Com); member(disease(D), Com) ), oaag:solve(description(D,disease(D,X,_,_,_,_,_,_))),!. %dev_query(X^info(X),_Com,notexist(info(X))). dev_query(X^info(X),_Com,fail(info(X))). dev_query( X^disease(X), Commitments, Answer):- not2neg(Commitments,Commitments0), oaag:solve(diagnose(Commitments0, queryResponse(PossibleDiseases,_RelSyms, _RelTests,_RelHist))), whatdisease0(PossibleDiseases,Commitments,Answer). dev_query( Q^bestq(Q), Commitments,Answer):- member(disease(Disease),Commitments), oaag:solve(description(Disease,disease(Disease, _Description,_Regions, symptoms(Symptoms), _Tests, history(History), _Treatment, _Prevention))),!, ( ( ( member(symptom(S,_,_),Symptoms), \+member(symptom(S),Commitments), \+member(not(symptom(S)),Commitments), \+member(rejected(symptom(S)),Commitments), Answer=bestq(symptom(S)) ) % false ; ( member(medicalHistory(H,_,_),History), \+member(medicalHistory(H),Commitments), \+member(not(medicalHistory(H)),Commitments), \+member(rejected(medicalHistory(H)),Commitments), Answer=bestq(medicalHistory(H)) ) ); Answer=fail(X^bestq(X)) ). dev_query( Q^bestq(Q), Commitments,Answer):- \+ member( disease(_), Commitments ), not2neg(Commitments,Commitments0), oaag:solve(diagnose(Commitments0, queryResponse(PossibleDiseases,RelSyms, RelTests,RelHist))), %if there is a best question Q the bestq(Q) else not(bestq(Q)) ( best_question(Commitments,PossibleDiseases,RelSyms,RelTests,RelHist,Q) -> Answer = bestq(Q); % Answer = not(bestq(Q)) Answer = fail(Q^bestq(Q)) ). %dev_query( Q^bestq(Q), _, fail(Q^bestq(Q)) ). %best labtest returns a ynq dev_query(X^best_labtest(X),Commitments,Answer):- member(disease(Disease),Commitments), oaag:solve(description(Disease,disease(Disease, _Description,_Regions,_Symptoms, tests(Tests),_History,_Treatment, _Prevention))),!, ( best_labtest(Commitments,Tests,Best) -> Answer = best_labtest(Best); Answer = not(best_labtest(_)) ). %dev_query(X^test_result(X),_Com,Answer1):- dev_query(test_result(_),_Com,Answer):- result_store(Answer). dev_do(take_test(T),_Com):- % member(best_labtest(T),Com), take_test(T). %_V�ldigt_ special purpose-predikat whatdisease0([],_Com,fail(X^disease(X),no_matches)). whatdisease0([D],_Com,disease(D)):-!. whatdisease0(_,_Com,fail(X^disease(X),too_many_matches)). %�nnu mer special purpose not2neg([],[]). not2neg([not(P)|Ps],[neg(P)|Qs]):- !, not2neg(Ps,Qs). not2neg([P|Ps],[P|Qs]):- not2neg(Ps,Qs). %detta predikat kan man �ndra i f�r att f� annan strategi %nu kollar det f�rst bland symptoms sedan bland history (inte bland tests - %de �r inte fr�gor) bryr sig inte om huruvida de �r 'reguired' eller inte best_question(Com,_,Syms,_Tests,Hist,Q):- ( member(P,Syms), P=symptom(C,_,_), Q=symptom(C) ; member(P,Hist), P=medicalHistory(C,_,_), Q=medicalHistory(C) ), \+member(rejected(Q),Com). %there is a nonrejected test for which the result is ot known best_labtest(Com,Tests,Best):- member(diagnosticTest(Best,_,_,required('yes'),_),Tests), \+member(test_result(Best),Com),% \+member(not(test_result(Best)),Com),% \+member(rejected(test_result(Best)),Com). dev_set(ID,Value) :- try(retract(variable_value(ID,_))), assert(variable_value(ID,Value)), ( user:flag(visualize_devices,yes) -> gfx_set_node_value(vcr,ID,Value) ; true ). dev_get(ID,Value) :- ( variable_value(ID,CurrentValue) -> Value = CurrentValue ; default_value(ID,Value) ) %,format(' *** ~a -> ~w\n',[ID,Value]) . dev_do(Command,Commitments) :- action(Command,Vars), set_command_variables(Vars,Commitments,Values), ( environment_mode(simulation) -> output_upnp(Command,Values) ; true ), perform_command(Command). set_command_variables([],_,[]). % 1-place propositions set_command_variables([Var|Vars],Commitments,[Val|Vals]) :- Com =.. [ Var, Val ], member(Com,Commitments), dev_set(Var,Val), set_command_variables(Vars,Commitments,Vals). % 0-place propositions set_command_variables([Prop|Vars],Commitments,[1|Vals]) :- Com =.. [ Prop ], member( Com, Commitments ), dev_set( Prop, 1 ), % 1 for true set_command_variables(Vars,Commitments,Vals). % 0-place propositions, negated set_command_variables([Prop|Vars],Commitments,[0|Vals]) :- Com =.. [ not, Prop ], member( Com, Commitments ), dev_set( Prop, 0 ), % 0 for false set_command_variables(Vars,Commitments,Vals). set_all_command_variables( [] ). set_all_command_variables( [Com | Coms] ):- Com =.. [ Pred | _ ], set_command_variables( [Pred], [Com], _ ), set_all_command_variables( Coms ). take_test( Test ):- retractall(result_store(_)), oaag:solve(tests(Tests)),!, member(diagnosticTest(Test,test(Type),result(Result),_,_),Tests), format('Test : ~a\n',[Type]), format('Result : ~a - y/n:\n',[Result]), get_nurse_test_input(C), ( C = y -> assert(result_store(test_result(Test))) ; assert(result_store(not(test_result(Test)))) ). get_nurse_test_input(C):- get_char(C0), ( member(C0,[y,n]), C=C0; write('please type \'y\' or \'n\''),!,nl, get_nurse_test_input(C)). valid_parameter( program_to_delete( N ) ):- dev_get( programs, Programs ), member( N:_, Programs ). perform_command( _ ) :- true. output_upnp(Command,Parameters) :- Term =.. [ Command | Parameters ], format('\n[UPnP] ~w\n\n',[Term]). try(G) :- ( G -> true ; true ).