Discussions related to Visual Prolog
larryhoughton
Posts: 11
Joined: 4 Oct 2016 21:16

Using "HasDomain" with a variable Domain parameter e.g. HasDomain(MyRuntimeVariableDomain,Term)

Unread post by larryhoughton »

Hi,
For retrieval of Terms from a Chain, can the "HasDomain" Domain parameter be set with a runtime variable (and reset during backtracking)?

Alternatively, I thought you could create a Domain with all of the Domains you would ever need (see below) and use that with HasDomain. My example below works for the first Domain (customers), but fails during the first backtrack, after successfully working with the first Domain (customers).
e.g.
domains
myData = c(customers);p(part_name, iD, customer_name).

Am I doomed to creating a Clause for each Chain solely for the purpose of setting the HasDomain parameter?

The dream is to scan through DB Chains dumping out the Terms as it backtracks. Below is the error I get during backtracking and my code snippet. Note that the Chain Name and Chain Domain are the same (e.g. Chain 'customers" has one Domain also named "customers"

********************
DB Name = Common.dba
NoOfTerms=8 MemSize=5968 DbaSize=6422 Free=2304217088
Chain name = customers
Term: customer("S1 Joe Fraser","S1 LA Ca")
Term: customer("S2 John Smith","S2 RSM Ca")
Term: customer("Joe Blow","Portland OR")
Term: customer("Sally Doe","Seattle Wa")
Chain name = parts
Exception in module: OneClass.exe
c:\program files (x86)\visual prolog 7.5\pfc\collection\algebraic\redblacktree\redblacktree.pro(252) : error r304: Invalid binary for the do
main 'data::customers' in ::toTerm( $[53,00,31,00,20,00,57,00,72,00 ... ] )

C:\Users\Administrator\Documents\Visual Prolog Projects\OneClass\Exe>pause
Press any key to continue . . .

Code: Select all

getChainInfo(MyDB):-     MyDB:db_chains(MyChain),     stdIO::write("\nChain name = ",MyChain), % hasDomain(MyChain,SomeTerm), %Above is what I wish would work because MyChain (by design) always equals the Chain's Term Domain.    hasDomain(customers,SomeTerm), %Always works for the customers Chain    MyDB:chain_terms(MyChain,SomeTerm, _), %Get the Term    stdIO::write("\nTerm: ",SomeTerm), %Print it    fail. %Backtracking to read the "parts" and "shipments" Chains and their Terms     /* notes */ % hasDomain(parts,SomeTerm),        %What I need for the first backtrack % hasDomain(shipments,SomeTerm), %What I need for the second backtrack % hasDomain(myData,SomeTerm),    %Trying a Domain with the 3 Domains above (customers, parts and Shipments). Always works for the customers Chain, but fails on backtracking (parts Domain) /* notes */   constants partChain = "parts". customerChain = "customers". shipmentChain ="shipments".     domains %myData = c(customers);p(parts);s(shipments). %Fails on backtrack %myData = p(parts);s(shipments);c(customers). %Fails on backtrack myData = c(customers);p(part_name, iD, customer_name);s(chaindb::ref,chaindb::ref). %Fails on backtrack   customers = customer(customer_name,address). parts = part(part_name, iD, customer_name). shipments = shipment(chaindb::ref,chaindb::ref).
Any thoughts?
Thanks in advance.
Larry
Martin Meyer
VIP Member
Posts: 328
Joined: 14 Nov 2002 0:01

Unread post by Martin Meyer »

Hi Larry,

maybe you are looking for a construction like this one:

Code: Select all

constants     customerChain = "customers".     partChain = "parts".     shipmentChain ="shipments".   domains     part_name = string.     iD = unsigned.     customer_name = string.     address = string.       customers = customer(customer_name, address).     parts = part(part_name, iD, customer_name).     shipments = shipment(chaindb::ref, chaindb::ref).       myData =         c(customers);         p(part_name, iD, customer_name);         s(chaindb::ref, chaindb::ref).   class predicates     insertSomeTestData : (chainDB MyDB). clauses     insertSomeTestData(MyDB) :-         MyDB:chain_insertz(customerChain, customer("S1 Joe Fraser", "S1 LA Ca"), _Customer_RefNumber_1),         MyDB:chain_insertz(customerChain, customer("S2 John Smith", "S2 RSM Ca"), Customer_RefNumber_2),         MyDB:chain_insertz(customerChain, customer("Joe Blow", "Portland OR"), _Customer_RefNumber_3),         MyDB:chain_insertz(customerChain, customer("Sally Doe", "Seattle Wa"), _Customer_RefNumber_4),         MyDB:chain_insertz(partChain, part("keyboard", 1, "S2 John Smith"), Part_RefNumber_1),         MyDB:chain_insertz(partChain, part("mouse", 2, "S2 John Smith"), Part_RefNumber_2),         MyDB:chain_insertz(partChain, part("monitor", 3, "Sally Doe"), _Part_RefNumber_3),         MyDB:chain_insertz(shipmentChain, shipment(Customer_RefNumber_2, Part_RefNumber_1), _Shipment_RefNumber_1),         MyDB:chain_insertz(shipmentChain, shipment(Customer_RefNumber_2, Part_RefNumber_2), _Shipment_RefNumber_2).   class predicates     getChainInfo : (chainDB MyDB). clauses     getChainInfo(MyDB) :-         MyDB:db_chains(MyChain),             stdIO::write("\nChain name = ", MyChain),             MyData = getChainInfo(MyDB, MyChain),                 stdIO::write("\n Term: ", MyData),                 fail.     getChainInfo(_MyDB).   class predicates     getChainInfo : (         chainDB MyDB,         string MyChain)         -> myData MyData         nondeterm. clauses     getChainInfo(MyDB, customerChain) = c(Customer) :-         MyDB:chain_terms(customerChain, Customer, _).     getChainInfo(MyDB, partChain) = p(PartName, ID, CustomerName) :-         MyDB:chain_terms(partChain, Part, _),         part(PartName, ID, CustomerName) == Part.     getChainInfo(MyDB, shipmentChain) = s(RefNumberA, RefNumberB) :-         MyDB:chain_terms(shipmentChain, Shipment, _),         shipment(RefNumberA, RefNumberB) == Shipment.   clauses     run() :-         MyDB = chainDB::db_create("MyDB", chainDB::in_memory),         insertSomeTestData(MyDB),         getChainInfo(MyDB).
It outputs:
  • Chain name = customers
    Term: c(customer("S1 Joe Fraser","S1 LA Ca"))
    Term: c(customer("S2 John Smith","S2 RSM Ca"))
    Term: c(customer("Joe Blow","Portland OR"))
    Term: c(customer("Sally Doe","Seattle Wa"))
    Chain name = parts
    Term: p("keyboard",1,"S2 John Smith")
    Term: p("mouse",2,"S2 John Smith")
    Term: p("monitor",3,"Sally Doe")
    Chain name = shipments
    Term: s(131072,327680)
    Term: s(131072,393216)
Regards Martin
larryhoughton
Posts: 11
Joined: 4 Oct 2016 21:16

Unread post by larryhoughton »

Hi Martin,
Thanks for the quick reply.
I was trying to have a single generic clause to handle all Domains, but the truth is; when I start creating the Prolog program that I really want to create, each Domain will need separate handling anyway. Your sample code is very clean and looks like exactly what I will want for my real world program.

Also, now I see how to setup MyData to accept all 3 Domains. All good stuff...
Thank you!
Larry
Post Reply