001: /*
002: * Copyright (C) 1999-2004 <A href="http://www-ist.massey.ac.nz/JBDietrich" target="_top">Jens Dietrich</a>
003: *
004: * This library is free software; you can redistribute it and/or
005: * modify it under the terms of the GNU Lesser General Public
006: * License as published by the Free Software Foundation; either
007: * version 2 of the License, or (at your option) any later version.
008: *
009: * This library is distributed in the hope that it will be useful,
010: * but WITHOUT ANY WARRANTY; without even the implied warranty of
011: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
012: * Lesser General Public License for more details.
013: *
014: * You should have received a copy of the GNU Lesser General Public
015: * License along with this library; if not, write to the Free Software
016: * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
017: */
018:
019: package org.mandarax.examples.crm.scripts;
020:
021: import org.mandarax.examples.crm.KBLoader;
022: import org.mandarax.examples.crm.PredicatesAndFunctions;
023: import org.mandarax.examples.crm.domainmodel.Category;
024: import org.mandarax.examples.crm.domainmodel.Customer;
025: import org.mandarax.examples.crm.domainmodel.Discount;
026: import org.mandarax.examples.crm.domainmodel.KindOfPayment;
027: import org.mandarax.kernel.*;
028: import org.mandarax.kernel.validation.TestCase;
029: import org.mandarax.lib.math.DoubleArithmetic;
030: import org.mandarax.reference.AdvancedKnowledgeBase;
031: import org.mandarax.util.*;
032: import org.mandarax.zkb.ZKBManager;
033:
034: import java.io.*;
035:
036: /**
037: * Executable utility class to generate the knowledge base and save it.
038: * This is usually done using a GUI application such as Oryx !
039: * This class showas how to create a kb manually and how to save it using ZKB.
040: * For storage we use a folder. If a file (not a folder) is passed to ZKB, the kb
041: * would be saved as a zip archive.
042: * @author <A href="http://www-ist.massey.ac.nz/JBDietrich" target="_top">Jens Dietrich</A>
043: * @version 3.4 <7 March 05>
044: * @since 3.4
045: */
046: public class Script2GenerateKB {
047: private static LogicFactorySupport lfs = new LogicFactorySupport();
048:
049: /**
050: * Constructor.
051: */
052: public Script2GenerateKB() {
053: super ();
054: }
055:
056: /**
057: * Run the script.
058: * @param arg runtime parameters
059: */
060: public static void main(String[] args) throws Exception {
061: File folder = KBLoader.KB_FOLDER;
062: if (!folder.exists()) {
063: folder.mkdir();
064: System.out.println("Created folder for example: " + folder);
065: } else if (!folder.isDirectory())
066: System.out.println("This should be a folder: " + folder);
067:
068: KnowledgeBase kb = buildKB();
069:
070: // this is the actual line to save the kb
071: new ZKBManager().exportKnowledgeBase(folder, kb);
072:
073: System.out.println("KB built and exported to: "
074: + folder.getAbsolutePath());
075: }
076:
077: /**
078: * Get the sample knowledge base. The knowledge base is hardcoded here,
079: * but should actually come from a data source.
080: * @return a knowledge base
081: */
082: public static KnowledgeBase buildKB() {
083: KnowledgeBase kb = new AdvancedKnowledgeBase();
084:
085: // useful variable .. the name of a customer type variable
086: String c = "a customer";
087:
088: // do lazy initialization
089: kb = new AdvancedKnowledgeBase();
090:
091: Rule rule1 = lfs.rule(lfs.prereq(DoubleArithmetic.GREATER_THAN,
092: lfs.cplx(PredicatesAndFunctions
093: .getFunctionTurnoverForKindOfPayment(), c,
094: new Integer(12), KindOfPayment.COMPANY_VISA),
095: new Double(200)), lfs.fact(PredicatesAndFunctions
096: .getPredicateHasCategory(), c, Category.PLATINUM));
097: Rule rule2 = lfs.rule(lfs.prereq(DoubleArithmetic.GREATER_THAN,
098: lfs.cplx(PredicatesAndFunctions.getFunctionTurnover(),
099: c, new Integer(12)), new Double(250)), lfs
100: .fact(PredicatesAndFunctions.getPredicateHasCategory(),
101: c, Category.GOLD));
102: Rule rule3 = lfs.rule(lfs.prereq(PredicatesAndFunctions
103: .getPredicateHasCategory(), c, Category.PLATINUM), lfs
104: .fact(PredicatesAndFunctions.getPredicateGetDiscount(),
105: c, new Discount(12.5)));
106: Rule rule4 = lfs.rule(lfs.prereq(PredicatesAndFunctions
107: .getPredicateHasCategory(), c, Category.GOLD), lfs
108: .fact(PredicatesAndFunctions.getPredicateGetDiscount(),
109: c, new Discount(7.5)));
110: Rule rule5 = lfs.rule(lfs.prereq(DoubleArithmetic.GREATER_THAN,
111: lfs.cplx(PredicatesAndFunctions.getFunctionTurnover(),
112: c, new Integer(12)), new Double(100)), lfs
113: .fact(PredicatesAndFunctions.getPredicateGetDiscount(),
114: c, new Discount(5)));
115:
116: // last rule is actually a fact! .. by default, each customer deserves a discount (to make him or her feel good and sell more .. that's business logic)
117: Fact rule6 = lfs.fact(PredicatesAndFunctions
118: .getPredicateGetDiscount(), c, new Discount(2.5));
119:
120: Predicate[] predicates = { DoubleArithmetic.GREATER_THAN };
121:
122: kb.add(rule1);
123: kb.add(rule2);
124: kb.add(rule3);
125: kb.add(rule4);
126: kb.add(rule5);
127: kb.add(rule6);
128:
129: // aliases - we use the general purpose properties interface to associate english sentences with rules
130: // an alternative approach would be to generate them, see Oryx for details on how this can be done
131: rule1
132: .setProperty(
133: "alias",
134: "if the turnover of a customer in the last 12 months payed with COMPANY VISA is more than US$ 200.00 then a customer has customer category Platinum");
135: rule2
136: .setProperty(
137: "alias",
138: "if the turnover of a customer in the last 12 months is more than US$ 250.00 then a customer has customer category Gold");
139: rule3
140: .setProperty(
141: "alias",
142: "if a customer has customer category Platinum then a customer gets a discount of 12.5%");
143: rule4
144: .setProperty(
145: "alias",
146: "if a customer has customer category Gold then a customer gets a discount of 7.5%");
147: rule5
148: .setProperty(
149: "alias",
150: "if the turnover of a customer in the last 12 months is more than US$ 100.00 then a customer gets a discount of 5.0%");
151: rule6.setProperty("alias",
152: "each customer gets a discount of 2.5%");
153:
154: // some test cases
155: Customer customer1 = new Customer(42, "John", "Smith");
156: Fact[] assumptions1 = { lfs.fact(PredicatesAndFunctions
157: .getPredicateHasCategory(), customer1,
158: Category.PLATINUM) };
159: Query query1 = lfs.query(lfs.fact(PredicatesAndFunctions
160: .getPredicateGetDiscount(), customer1, new Discount(
161: 12.5)),
162: "Test whether platinum customers get 12.5 % discount");
163: TestCase tc1 = LogicFactory.getDefaultFactory().createTestCase(
164: query1, assumptions1, TestCase.AT_BOTTOM, true);
165: kb.addTestCase(tc1);
166:
167: // test2 relies on the fact that the dummy method Customer#getTurnover returns 1000 by default
168: Customer customer2 = new Customer(42, "John", "Smith");
169: Fact[] assumptions2 = {};
170: Query query2 = lfs.query(lfs.fact(PredicatesAndFunctions
171: .getPredicateHasCategory(), customer2,
172: Category.PLATINUM),
173: "Test the condition for a PLATINUM customer");
174: TestCase tc2 = LogicFactory.getDefaultFactory().createTestCase(
175: query2, assumptions2, TestCase.AT_BOTTOM, true);
176: kb.addTestCase(tc2);
177:
178: return kb;
179: }
180:
181: }
|