How to set it up Example - NMAI-lab/JLOAF GitHub Wiki
EDIT REQUIRED FOR train(Reasoning(CaseBase))
This is a simple example that could help the user understand the steps they must go through in order to set an agent of any domain in our framework, and test it or run it. First, let’s start with a brief explanation of the agent’s behavior: The agent simply takes an integer x as an input and returns an integer x+1 as an output. To set this agent up, one must follow these steps:
1- Create an Agent Class that extends the Agent class in our frame work. This will force you to create a constructor in you agent class, so you can call the super constructor in it.
Figure 1.
As you can see in Figure 1 above, you do not have to worry about what to pass to the super constructor, just pass them null for now.
2- Override two of the super class methods, one is the run method, the second is the train method.
Figure 2.
As you can see in figure 2, the run method takes an Input as an argument and returns an action. This is the method that will be used by your agent to predict the actions of you agent after you have trained it; but how do we train it you might ask? Well the answer lies in the train method.
The train method takes a reasoner r as an argument and does not return anything. The “Reasoning” object represents the reasoning your agent is going to use to predict actions once it receives a new input. The Reasoner takes a casebase, which holds cases from previous experiments of your Agent. To know more about the reasoning class and the different reasoners the jloaf framework supports, you can go to Reasoning.
Now After finishing the agent class, you are almost done! The only thing that you have left is the create your case base, and that is an easy task for the most part of it. To create a caseBase you have two options:
1- Parse a log file with all the previous experiments of your agent into a case base
2- Create the case base manually.
In both cases, one must have some idea about the structure of the Casebase, Case, Input, and Action classes in our framework. To obtain that knowledge, we strongly recommend that you visit: inputs and actions Now that you have an idea about the structure of the casebase in jloaf, let us start talking about the second option. To create a casebase manually, these are the steps one shall follow:
1- Create an instance of the casebase class. The caseBase will originally be empty.
2- Create inputs that are compatible with the domain of their agent (atomic, complex).
3- Create Actions that are compatible with the domain of their agent (Atomic, Complex).
4- For each input and action pair class the createThenAdd method of you casebase instance, and pass it those input and action pair.
After Adding all the inputs and the actions that you must add, your casebase would be complete, and you would be able to start your testing right away. Here’s an example from our sample agent that shows how to manually create your case base, and train your agent with it.
Figure 3.
As you can see, in our sample agent, only Atomic inputs were used, given the simplicity of our domain’s inputs. We started by creating Features for our inputs, since each atomic input must have a feature. Then we created The Actions that correspond to our inputs, and then we called the createThenAdd method passing it pairs of inputs and Actions. Notice here two things that we haven’t mentioned before, atomicStrategy and stateStrategy. The atomicStrategy is an instance of the AtomicSimilarityMetricStrategy, this is the strategy that is used by the agent’s reasoner to compare Atomic inputs with each other and you must pass it upon creating new atomic inputs.There is a wide selection of those strategies supported by our frame work.
The stateStrategy is an instance of the StateBaseSimilarity class, again it is also the strategy used by the agent’s reasoner to compare runs with each other and you must pass it to the createThenAdd method. For more information about the Strategies supported by our framework visit strategies
The last line of the figure above, shows how you are supposed to pass your newly created casebase to a Reasoner then pass that reasoner to the agent. After the previous steps are done, all you have to do is to test/run your agent.
Now for the first option, where all you have to do is to parse your log file (the file that has data about your previous experiments) into a case base. Note that the techniques of parsing are of the user’s choice, but we are just giving you an example of how it might be structured.
Figure 4.
As you can see in the figure above a class for the parser was created, and it has two fields, which are two similarityStrategies that were instantiated, so they can be used for the creation of the inputs. Its always highly recommended to have a single instance of the inputs Similarity Strategies.
Figure 5.
As you can see in figure 5, our parser class has a method called parseLogFile, that takes two arguments; One is the name of the log file and the other is the name of the output file, the output file is where we are going to save our casebase as a written object. The steps to parsing our log file are as follow: 1- initializing an empty casebase that we are going to add our cases to.
2- Looping through the whole log file. In our case we used a Scanner object that will loop through a text file, which is the format of our log file. Our log file is an nx2 matrix where each row represents a case, and the two columns represent the input and the action of that case. The while loop in our example goes through each cell at a time and store the value of that cell in an array of integers of size 2, and every time we store two integers in our array we create the corresponding case.
3- Creating the inputs and the Actions. In our example, as mentioned above, we create a case every two loops, that is after we have two new numbers in our array of integers. The first thing we do, is to create the Atomic Input, that takes a feature, which takes a value, which is the value of index zero in the “entry” array. Note that in our case the name of the input does not matter, and the strategy passed to the input is the atomicStrategy field. After creating the input, we create the Action, which is an Atomic Action for our example. In our case the name of the Action is what represents the Action itself, so the second element of the “entry” array, which is an integer, was passed to the name of the Atomic input.
4- After creating each input and action, we must create the case that holds them, then add it to the casebase. Luckily, we have a method that does this for you, as mentioned previously, it is the createThenAdd method.
5- After we looped through the whole log file, we saved our casebase into an out put file using the static method “save” in the casebase class, this methods writes java objects into text files, so all we did was passing the casebase and the name of the output file to the save method, and it did all the work for us. 6- We returned the name of the file that holds the casebase, so that it can be used when running or testing our agent.
Although it is not shown in our example, the way to train the agent with the created case base is described previously in this page, all you have to do is the following : agent.train(reasoner(CaseBase.load(filename)). The load function in the case base loads a written casebase to a java object.
For more information about how to run our frame work, please visit: How to Run