NETICA COM INTERFACE - VISUAL BASIC PROGRAMMING 2007-01-04 ------------------------------------------------- IMPORTANT: There is better documentation than this available. Run Netica Application and choose Help -> Contents/Index from the overhead menu. From the Index tab, look up 'Visual Basic programming'. This document is to get you started programming Netica via its COM interface (also known as ActiveX or Automation). You can program Netica through its COM interface using any computer language that can access a COM interface; for example Visual Basic (VB), C#, COM enabled Java, or C++. The below is written as though VB is being used, but it pertains to programming in the other languages as well. If you have programmed an MS Office product using Visual Basic, you will find some similarities in style with the Netica COM interface. To use Netica COM in its fully enabled form, you must have a Netica license password that is for both Netica Application and Netica API. First, run the latest version (must be version 3.10 or greater) of Netica Application, so it can register itself in the registry. If you have several versions of Netica on your computer, the version of Netica that VB will use will always be the one that was last run (for example, by double-clicking it). You can leave it running or exit it. Then to get access to it from Visual Studio, choose Project->Add Reference from Visual Studio, click the "COM" tab if necessary, and checkmark the entry called "Netica 1.0 Object Library" (with perhaps some other version number). You can then use the object browser to see the Netica objects and functions available. Choose View->Object Browser or View->Other Windows->Object Browser, and then: In Visual Studio 6, set the library to Netica in the upper left choice box. In Visual Studio .NET or VS 2005: In the left pane of the Object Browser, one of the top level entries will be "Interop.Netica". You can browse that, but it won't be as good as browsing the Netica library directly, because it won't have a description of each function, and it may not even list the functions at all. If there is no entry at the top level for the library named simply "Netica" (with the books icon), choose "Edit Custom Component Set..." from the "Browse" menu on the toolbar of the Object Browser (with VS.Net 2003, click on the "Customize..." button at the top of the window, and then the "Add..." button of the dialog box that appears). Choose the COM tab, select the Netica library from the list, click "Add" or "Select" and then "OK". Now the books icon for the Netica library should appear, and you can browse it. In the object browser, when you click on any function or enum, then a short description will appear, which is good enough for most programming work. If you need more detail, then you will notice that at the end of the description is the name of the equivalent function in the Netica-C API. You can look up that function in the Netica-C documentation. To view that documentation, see: http://www.norsys.com/onLineAPIManual/index.html and to download it, go to: http://www.norsys.com/download_api.html A great benefit of programming Netica.exe through its COM interface is that people can interact with the GUI at the same time as your VB program is running. That can be useful for debugging, demos, and distributing products that allow the end-user to interact directly with the Bayes net. If your license password enables only Netica API, then the GUI will operate in a limited mode, and if your license password enables only Netica Application, then your VB calls to Netica will operate in a limited mode. If you want to distribute your VB program that uses Netica, you need to only send Netica.exe (and perhaps Netica.hlp), but not Netica.dll. Make sure you have the required license from Norsys before you do so. You can use the 'Visible' property of the Netica.Application object to determine whether or not the graphical user interface (GUI) is present or not (by setting it to true or false, see the example below). If it is not visible, then it will be a minimized window appearing only as an icon on the task bar. If you wish to prevent the user from un-minimizing it, thereby preventing them from having access to the Netica GUI, set the 'UserAllowed' property of Netica.Application to false. To start up Netica so that it operates with a password that is not put in the Registry, start it from your VB program with the command line argument -password followed by the password you want Netica to use. That password will not be entered into the registry, and its security part will not be visible to the user. So your program might have a part looking something like this: Shell ("C:\\Netica\\Netica217\\Netica.exe -password +...310-3-E/...") Dim app As New Netica.Application app.Visible = False app.UserAllowed = False ... app.Quit To make a continuous node, simply create one passing 0 for the number of states. To later discretize it, or set the levels of an already discrete node (equivalent to the C function SetNodeLevels_bn), simply change its "Level" property. You just set Node.Level(0), then Node.Level(1), etc. It will adust the number of states of the node each time. If you have very many states, you may want to start with the highest first, since that is somewhat more efficient. Note that in versions of Netica prior to version 3.04, there are some problems with this function. Below is an example VB program that does the same thing as the "Demo" program that ships with Netica C-API, and also one that reads in a net from the Examples folder (you may have to change the path), then reads in cases and does belief updating. ------------------------------ Private Sub Manual1_Click() On Error GoTo err Dim app As Netica.Application Dim net As BNet Dim TB As BNode Dim belief As Double Set app = New Netica.Application app.Visible = True Set net = app.ReadBNet (app.NewStream("C:\Netica Data\ChestClinic.dne"), "") net.Compile Set TB = net.Nodes("Tuberculosis") belief = TB.GetBelief("present") MsgBox "The probability of tuberculosis is " & belief net.Nodes("XRay").EnterFinding ("abnormal") belief = TB.GetBelief("Present") MsgBox "Given an abnormal X-Ray, the probability of tuberculosis is " & belief net.Nodes("VisitAsia").EnterFinding ("visit") belief = TB.GetBelief("Present") MsgBox "Given abnormal X-Ray and visit to Asia, the probability of tuberculosis is " & belief net.Delete If Not app.UserControl Then app.Quit End If Exit Sub err: MsgBox "API_Demo1: Error " & ((err.Number And &H7FFF) - 10000) & ": " & err.Description End Sub ------------------------------ Private Sub Command2_Click() On Error GoTo err_Generic Dim casefile As Streamer Dim app As Application Dim lights_node As BNode Dim lights_dim As Long Dim net As BNet Set app = New Netica.Application Set netfile = app.NewStream("C:\Netica Data\BNs\Car_Diagnosis_0_Learned.dne") Set casefile = app.NewStream("C:\Netica Data\Cases\Good Cases\Car Cases 10.cas") 'The function NewStream may be called FileNamed in older versions of Netica Set net = netfile.ReadBNet(2) net.AutoUpdate = 1 net.Compile Set lights_node = net.Nodes("Lights") lights_dim = lights_node.StateNumber("dim") Dim id As Long Dim fr As Double Dim caseposn As Long Dim done As Boolean done = False caseposn = FirstCase Do net.RetractFindings net.Nodes.ReadCase case_posn:=caseposn, stream:=casefile, IDNum:=id, freq:=fr If caseposn = NoMoreCases Then done = True Else MsgBox "Belief in Lights dim = " & lights_node.GetBelief(lights_dim) End If caseposn = NextCase Loop Until done net.Delete Exit Sub err_Generic: MsgBox "Error " & ((err.Number And &H7FFF) - 10000) & ": " & err.Description End Sub =============================================================================== EXAMPLES ON HOW TO SET CPT TABLE ENTRIES: ---------------------------------------- Here is how you could set the CPTs of the "Chest Clinic" example from the manual: Dim VisitAsia As BNode, Tuberculosis As BNode, Smoking As BNode Dim Cancer As BNode, XRay As BNode, TbOrCa As BNode Set VisitAsia = net.Nodes("VisitAsia") ... Set TbOrCa = net.Nodes("TbOrCa") Dim p(0 To 1) As Single p(0) = 0.01: p(1) = 0.99: VisitAsia.CPTable("") = p p(0) = 0.05: p(1) = 0.95: Tuberculosis.CPTable(Array(0)) = p p(0) = 0.01: p(1) = 0.99: Tuberculosis.CPTable(Array(1)) = p p(0) = 0.5: p(1) = 0.5: Smoking.CPTable("") = p p(0) = 0.1: p(1) = 0.9: Cancer.CPTable(Array(0)) = p: p(0) = 0.01: p(1) = 0.99: Cancer.CPTable(Array(1)) = p p(0) = 0.98: p(1) = 0.02: XRay.CPTable(Array(0)) = p p(0) = 0.05: p(1) = 0.95: XRay.CPTable(Array(1)) = p p(0) = 1: p(1) = 0: TbOrCa.CPTable(Array(0, 0)) = p: p(0) = 1: p(1) = 0: TbOrCa.CPTable(Array(0, 1)) = p: p(0) = 1: p(1) = 0: TbOrCa.CPTable(Array(1, 0)) = p: p(0) = 0: p(1) = 1: TbOrCa.CPTable(Array(1, 1)) = p: Here are 6 alternate ways to set the CPT of the TbOrCa node. Dim p(0 To 1) As Single Dim s(0 To 1) As Integer s(1) = 0: s(0) = 0: p(0) = 1: p(1) = 0: TbOrCa.CPTable(s) = p: s(0) = 1: TbOrCa.CPTable(s) = p: s(1) = 1: s(0) = 0: TbOrCa.CPTable(s) = p: s(0) = 1: p(0) = 0: p(1) = 1: TbOrCa.CPTable(s) = p: Dim p(0 To 1) As Single p(0) = 1: p(1) = 0: TbOrCa.CPTable("present,present") = p: p(0) = 1: p(1) = 0: TbOrCa.CPTable("present,absent") = p: p(0) = 1: p(1) = 0: TbOrCa.CPTable("absent,present") = p: p(0) = 0: p(1) = 1: TbOrCa.CPTable("absent,absent") = p: TbOrCa.StateFuncTable("present,present") = "true": TbOrCa.StateFuncTable("present,absent") = "true": TbOrCa.StateFuncTable("absent,present") = "true": TbOrCa.StateFuncTable("absent,absent") = "false": TbOrCa.CPTable("*,*") = Array(1, 0) TbOrCa.CPTable("absent,absent") = Array(0, 1) TbOrCa.StateFuncTable("*,*") = "true" TbOrCa.StateFuncTable("absent,absent") = "false" TbOrCa.Equation = "TbOrCa (Tuberculosis, Cancer) = (Tuberculosis || Cancer)" TbOrCa.EquationToTable num_samples:=1, samp_unc:=False, add_exist:=False