Giter Club home page Giter Club logo

symbolicreasoningengine's Introduction

SymbolicReasoningEngine

A powerful symbolic reasoning engine designed for dynamic knowledge inference and decision-making based on logical rules and facts.

Overview

The SymbolicReasoningEngine is a flexible and extensible framework that enables symbolic reasoning processes. It allows for the representation and manipulation of knowledge through facts and rules, supporting the evaluation of complex logical expressions. This engine is capable of dynamic inference, making it suitable for a wide range of applications from artificial intelligence solutions to expert systems and educational tools.

Features

  • Dynamic Knowledge Base: Manage a growing knowledge base of facts that the engine uses for reasoning.
  • Logical Rule Evaluation: Define rules with premises and conclusions to drive the inference process.
  • Variable Support: Utilize variables within rules for dynamic and context-sensitive reasoning.
  • Backward Chaining: Apply backward chaining logic to search for matching goals within specified rules.
  • Forward Chaining: Apply forward chaining logic to automatically derive new facts from existing ones.
  • Extensible Design: Easily extend the engine to accommodate new types of logical operations or domain-specific optimizations.

Getting Started

To get started with the SymbolicReasoningEngine, clone this repository and include it in your project. Ensure you have Rust installed on your system to compile and run the engine.

git clone https://github.com/TheTekton337/SymbolicReasoningEngine.git
cd SymbolicReasoningEngine
cargo build

Usage Examples

Here's a simple example of how to use the SymbolicReasoningEngine to define symbols, assert variables and facts, add rules, and perform inference with forward chaining:

let mut engine = SymbolicReasoningEngine::new();

// Define symbols
let weather_symbol = engine.define_symbol("Weather", "String");
let activity_symbol = engine.define_symbol("Activity", "String");

// Assert the variable temp = 30
let temp_variable = Variable { name: "temp".to_string(), value: FactValue::Integer(30), state: VariableState::Stable };
engine.assert_variable(&temp_variable);

// Assert the fact: It is sunny
engine.assert_fact(weather_symbol.clone(), FactValue::Text("Sunny".to_string()));
engine.assert_fact(temp_symbol.clone(), FactValue::Text("${temp}".to_string()));

// Define the rule: If it is sunny, then it's a good day for outdoor activity
engine.define_rule(
    LogicalOperator::And(vec![
        LogicalOperator::AtomicFact(Fact {
            symbol: weather_symbol.clone(),
            value: FactValue::Text("Sunny".to_string()),
        }),
        LogicalOperator::GreaterThan(
            Box::new(ComparableValue::Direct(FactValue::Text("${temp}".to_string()))),
            Box::new(ComparableValue::Direct(FactValue::Integer(20)))
        )
    ]),
    Fact {
        symbol: activity_symbol.clone(),
        value: FactValue::Text("Outdoor".to_string()),
    },
);

// Perform forward chaining to infer new facts based on the rules
engine.forward_chaining();

// Check if the new fact (good day for outdoor activity) is added to the knowledge base
assert!(engine.facts.contains(&Fact {
    symbol: activity_symbol,
    value: FactValue::Text("Outdoor".to_string()),
}), "The engine did not infer that it's a good day for outdoor activity when it's sunny.");

Here is a simple example of how to use the SymbolicReasoningEngine to define symbols, assert facts, add rules, and perform inference via backward chaining:

let mut engine = SymbolicReasoningEngine::new();

// Define symbols
let weather = engine.define_symbol("Weather", "String");
let temperature = engine.define_symbol("Temperature", "Integer");

// Assert known facts into the engine's knowledge base
engine.assert_fact(temperature.clone(), FactValue::Integer(25));
engine.assert_fact(weather.clone(), FactValue::Text(String::from("Sunny")));

// Rule 1: If temperature > 20, then it's warm
let warm = engine.define_symbol("warm", "Boolean");
engine.define_rule(
    LogicalOperator::GreaterThan(
        Box::new(ComparableValue::Symbol(temperature.clone())),
        Box::new(ComparableValue::Direct(FactValue::Integer(20)))
    ),
    // Fact::new(warm.clone(), FactValue::Boolean(true))
    Fact::new(warm.clone(), FactValue::Text("Warm".into()))
);

// Rule 2: If it's warm and sunny, then it's a good day for a picnic
let picnic_day = engine.define_symbol("picnic_advisable", "Boolean");
engine.define_rule(
    LogicalOperator::And(vec![
        LogicalOperator::AtomicFact(Fact::new(warm.clone(), FactValue::Text("Warm".into()))),
        LogicalOperator::AtomicFact(Fact::new(weather.clone(), FactValue::Text(String::from("Sunny"))))
    ]),
    Fact::new(picnic_day.clone(), FactValue::Boolean(true))
);

// Specify the goal: To determine if it's a picnic day
let goal = Fact::new(picnic_day, FactValue::Boolean(true));
let is_picnic_day = engine.specify_goal(&goal);

// Assert that the engine successfully determines it's a beach day through backward chaining
assert!(is_picnic_day, "The engine should successfully determine it's a picnic day through backward chaining.");

Documentation

For detailed documentation on using the SymbolicReasoningEngine, including all available methods and their usage, please refer to the doc directory in this repository.

Contributing

We welcome contributions to the SymbolicReasoningEngine project! Please refer to our Contributing Guide for more information on how to get involved.

License

This project is licensed under the Unlicense - see the LICENSE file for details.

symbolicreasoningengine's People

Contributors

thetekton337 avatar

Stargazers

Kyle McCarthy avatar

Watchers

 avatar

symbolicreasoningengine's Issues

Add support for knowledge base providers

Currently, the knowledge base is a simple in-memory store. Add support for additional knowledge base providers. Also, will need to review other knowledge base projects for standard practices, etc.

Add providers for Facts, Rules, and FactValues

Modular Source Providers Plan

This rough draft outlines a modular approach to adding support for file, API, and syscall sources for Facts, Rules, and FactValues in the SymbolicReasoningEngine. Each source provider should be independently implemented and easily swapped.

1. Define Source Provider Traits:

Create traits for different source providers, such as FileSourceProvider, ApiSourceProvider, and SyscallSourceProvider. Each trait should define methods for retrieving Facts, Rules, and FactValues from their respective sources.

trait FileSourceProvider {
    fn load_facts_from_file(&self, file_path: &str) -> Vec<Fact>;
    fn load_rules_from_file(&self, file_path: &str) -> Vec<Rule>;
    // ... other methods for FileSourceProvider
}

trait ApiSourceProvider {
    fn fetch_facts_from_api(&self, endpoint: &str) -> Vec<Fact>;
    fn fetch_rules_from_api(&self, endpoint: &str) -> Vec<Rule>;
    // ... other methods for ApiSourceProvider
}

trait SyscallSourceProvider {
    fn get_facts_from_syscall(&self) -> Vec<Fact>;
    fn get_rules_from_syscall(&self) -> Vec<Rule>;
    // ... other methods for SyscallSourceProvider
}

2. Implement Source Provider Modules:

Create modules that implement the defined traits. For example, you might have a FileSourceProviderImpl, ApiSourceProviderImpl, and SyscallSourceProviderImpl implementing the corresponding traits.

struct FileSourceProviderImpl;

impl FileSourceProvider for FileSourceProviderImpl {
    // Implement methods for loading facts, rules, and other data from files
}

struct ApiSourceProviderImpl;

impl ApiSourceProvider for ApiSourceProviderImpl {
    // Implement methods for fetching facts, rules, and other data from APIs
}

struct SyscallSourceProviderImpl;

impl SyscallSourceProvider for SyscallSourceProviderImpl {
    // Implement methods for getting facts, rules, and other data from syscalls
}

3. Update SymbolicReasoningEngine to Use Source Providers:

Modify the SymbolicReasoningEngine to accept instances of these source providers during initialization.

struct SymbolicReasoningEngine {
    file_source_provider: Box<dyn FileSourceProvider>,
    api_source_provider: Box<dyn ApiSourceProvider>,
    syscall_source_provider: Box<dyn SyscallSourceProvider>,
    // ... other fields
}

impl SymbolicReasoningEngine {
    pub fn new(
        file_source_provider: Box<dyn FileSourceProvider>,
        api_source_provider: Box<dyn ApiSourceProvider>,
        syscall_source_provider: Box<dyn SyscallSourceProvider>,
    ) -> Self {
        // Initialize the engine with the provided source providers
        SymbolicReasoningEngine {
            file_source_provider,
            api_source_provider,
            syscall_source_provider,
            // ... initialize other fields
        }
    }

    // ... other methods for the engine
}

4. Add Methods to Load Data from Sources:

Implement methods in SymbolicReasoningEngine that use the source providers to load Facts, Rules, and other data from different sources.

impl SymbolicReasoningEngine {
    pub fn load_facts_from_file(&self, file_path: &str) -> Vec<Fact> {
        self.file_source_provider.load_facts_from_file(file_path)
    }

    pub fn fetch_facts_from_api(&self, endpoint: &str) -> Vec<Fact> {
        self.api_source_provider.fetch_facts_from_api(endpoint)
    }

    pub fn get_facts_from_syscall(&self) -> Vec<Fact> {
        self.syscall_source_provider.get_facts_from_syscall()
    }

    // ... similar methods for rules and other data
}

5. Usage Example:

fn main() {
    // Create instances of source providers
    let file_source_provider = Box::new(FileSourceProviderImpl);
    let api_source_provider = Box::new(ApiSourceProviderImpl);
    let syscall_source_provider = Box::new(SyscallSourceProviderImpl);

    // Create the SymbolicReasoningEngine with the source providers
    let engine = SymbolicReasoningEngine::new(file_source_provider, api_source_provider, syscall_source_provider);

    // Use engine methods to load data from different sources
    let facts_from_file = engine.load_facts_from_file("/path/to/facts.json");
    let facts_from_api = engine.fetch_facts_from_api("http://api.example.com/facts");
    let facts_from_syscall = engine.get_facts_from_syscall();

    // ... perform other operations with the engine
}

Refactor SymbolicReasoningEngine so it isn't monolithic

Currently, this project has all of its code in lib.rs. Being new to rust, the last time I went to organize modules in a rust project, it was more involved than I expected and set it aside for later. I'll use this refactoring to learn how to organize rust code and better organize the codebase.

README updates needed

  • Add project origins and goals.
  • Add links to relevant research papers.
  • Add roadmap.

Confusing comparable value types for variables

String interpolation from variables via ComparableValue::Direct(FactValue::Text("...".to_string())) is confusing. I think ComparableValue::Variable("varName".to_string()) is much more straight forward. If Box isn't necessary or can be done within the method itself, readability should improve. Also, probably should review Direct type... perhaps it would be better to have Integer, Float, etc first-class for ComparableValue.

LogicalOperator::GreaterThan(
    Box::new(ComparableValue::Direct(FactValue::Text("${temp}".to_string()))),
    Box::new(ComparableValue::Direct(FactValue::Integer(20)))
)

vs

LogicalOperator::GreaterThan(
    ComparableValue::Variable("temp".to_string()),
    ComparableValue::Integer(20)
)

NSCR planning: NeuralNetworkEngine and IntegrationEngine

Integration Layer Plan for NSCR Framework

The NSCR (Neuro-Symbolic Cognitive Reasoning) framework involves integrating the SymbolicReasoningEngine with a neural network engine and an integration engine.

Plan Summary:

The NSCR framework aims to seamlessly integrate symbolic reasoning with neural network capabilities through the Integration Engine. By defining common data representations, protocols, and feedback mechanisms, this framework will allow for a combination of symbolic and neural reasoning to tackle complex cognitive tasks.

Components:

  1. SymbolicReasoningEngine (SRE):

    • This is the core reasoning engine based on symbolic reasoning.
    • It handles logical rules, facts, and inference.
  2. Neural Network Engine (NNE):

    • Responsible for training and executing neural networks.
    • Deals with pattern recognition, learning from data, and complex non-linear relationships.
  3. Integration Engine (IE):

    • Serves as the middleware that connects SRE and NNE.
    • Manages communication and data flow between symbolic reasoning and neural network processing.

Plan:

1. Define a Common Data Representation:

  • Establish a common format for representing facts, rules, and inputs/outputs that both SRE and NNE can understand.
  • This could be a shared data structure or a standard data interchange format.

2. Data Exchange Protocols:

  • Define protocols for exchanging data between SRE, NNE, and IE.
  • Consider using standard formats like JSON or Protocol Buffers for seamless communication.

3. SRE Changes:

  • Modify SRE to expose interfaces for:
    • Accepting input data in the common format.
    • Retrieving output in the common format.
  • Enhance SRE to work with continuous data flows, as neural networks often require iterative training.

4. IE Implementation:

  • Create the Integration Engine (IE) to facilitate communication between SRE and NNE.
  • IE should handle data preprocessing, passing data between SRE and NNE, and handling feedback loops.

5. Integration Logic:

  • Implement logic within IE to decide when to involve the neural network engine based on certain conditions.
  • Define rules for deciding whether to delegate to the neural network or rely solely on symbolic reasoning.

6. Feedback Mechanism:

  • Establish a feedback mechanism where the output from NNE influences the symbolic reasoning in SRE and vice versa.
  • Ensure that learning from data is integrated into the overall reasoning process.

7. Testing and Validation:

  • Rigorous testing is crucial to ensure the seamless integration of SRE, NNE, and IE.
  • Implement test cases that cover various scenarios, including cases where neural network results affect symbolic reasoning and vice versa.

8. Documentation:

  • Provide clear documentation for developers and users explaining how to use the integrated NSCR framework.
  • Include guidelines on configuring, training, and maintaining the system.

9. Example Use Cases:

  • Create example use cases or applications that showcase the synergies between symbolic reasoning and neural networks in the NSCR framework.
  • Demonstrate how the combined capabilities of SRE and NNE lead to more powerful and flexible reasoning.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.