命题逻辑自动证明机(C#实现)

命题逻辑自动证明机
主要实现的步骤如下,其实都是比较简单的逻辑实现:
1. 命题逻辑语句中和计算机逻辑运算等价部分的替换;
2. 命题逻辑规则中比较特殊的规则,转换成计算机可识别的逻辑运算;
3. 将处理完成的命题等价字符串动态拼接进C#源代码;
4. 调用C#编译器接口动态编译源代码,调用程序运算并得出结果;

using Microsoft.CSharp;
using System;
using System.CodeDom.Compiler;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;

namespace DynamicCompile
{
    public class DynamicCompiler
    {

        public static void Invoke(string Proposition)
        {
            #region 编译准备:语句+编译参数+编译语言
            // 1.命题逻辑语句预处理
            string sourceCode = GenerateCode(Proposition);

            // 2.CSharpCodePrivoder对象 
            CSharpCodeProvider objCSharpCodePrivoder = new CSharpCodeProvider();

            // 3.CompilerParameters参数 
            CompilerParameters objCompilerParameters = new CompilerParameters();
            objCompilerParameters.ReferencedAssemblies.Add("System.dll");//引用系统dll 
            objCompilerParameters.GenerateExecutable = false;
            objCompilerParameters.GenerateInMemory = true;

            // 4.CompilerResults,编译 
            CodeDomProvider kk = CSharpCodeProvider.CreateProvider("CSharp");
            CompilerResults cr = kk.CompileAssemblyFromSource(objCompilerParameters, new string[] { sourceCode });
            #endregion

            #region 动态编译源+执行代码
            if (cr.Errors.HasErrors)
            {
                Console.WriteLine("编译错误:");
                foreach (CompilerError err in cr.Errors)
                {
                    Console.WriteLine(err.ErrorText);
                }
            }
            else
            {
                // 通过反射,调用HelloWorld的实例 
                Assembly objAssembly = cr.CompiledAssembly;
                object objHelloWorld = objAssembly.CreateInstance("DynamicCodeGenerate.HelloWorld");
                MethodInfo objMI = objHelloWorld.GetType().GetMethod("OutPut");
                // 调用执行 
                Console.WriteLine(objMI.Invoke(objHelloWorld, null));
            }
            Console.ReadLine();
            #endregion
        }

        //动态生成代码串
        public static string GenerateCode( string Proposition)
        {

            #region 命题逻辑系统语句处理
            List<string> listAtomP=new List<string>();
            string strCode = Manager(Proposition);
            if (strCode.Contains("不是"))
            {
                strCode = "false";
            }
            else {
                listAtomP = DefineBool(strCode);
            }          
            #endregion

            #region 动态拼接程序源代码

            StringBuilder sb = new StringBuilder();
            sb.Append("using System;");
            sb.Append(Environment.NewLine);
            sb.Append("namespace DynamicCodeGenerate");
            sb.Append(Environment.NewLine);
            sb.Append("{");
            sb.Append(Environment.NewLine);

            #region 其他源码传入程序测试
            //sb.Append(Proposition);
            #endregion

            #region hello,world逻辑语句验证
            sb.Append(" public class HelloWorld");
            sb.Append(Environment.NewLine);
            sb.Append(" {");
            sb.Append(Environment.NewLine);
            sb.Append(" public string OutPut()");
            sb.Append(Environment.NewLine);
            sb.Append(" {");
            sb.Append(Environment.NewLine);
            for (int i = 0; i < listAtomP.Count; i++)
            {
                sb.Append(" bool " + listAtomP[i] + "=true;");
            }
            sb.Append(" if(" + strCode + ")");
            sb.Append(Environment.NewLine);
            sb.Append(" {return \"该命题成立!\";}");
            sb.Append(Environment.NewLine);
            sb.Append(" else");
            sb.Append(Environment.NewLine);
            sb.Append(" {return \"该命题不成立!\";}");
            sb.Append(Environment.NewLine);
            sb.Append(" }");
            sb.Append(Environment.NewLine);
            sb.Append(" }");
            #endregion

            sb.Append(Environment.NewLine);
            sb.Append("}");

            #endregion

            #region 打印/返回代码

            string code = sb.ToString();

            Console.WriteLine(code);
            Console.WriteLine();
            return code;

            #endregion
        } 

        /// <summary>
        /// 命题正规化
        /// </summary>
        /// <param name="Proposition"></param>
        /// <returns></returns>
        public static string Manager(string Proposition)
        {

            //合式公式判定
            int flag=isWFF(Proposition);

            if(flag!=0)
            {
                return "该命题不是合式公式!";
            }
            else
            {   
                //符号替换(消去↔,﹁)
                Proposition=SymbolRepalce(Proposition);

                //正规化(消去→)具体算法,参考之前命题逻辑系统中完备性证明
                Proposition = Formalize(Proposition);
            }

            return Proposition;     

        }

        /// <summary>
        /// 判定命题是否是合式公式
        /// </summary>
        /// <param name="StrPro"></param>
        /// <returns></returns>
        private static int isWFF(string StrPro)
        {
            int flag=0;
            //消去语句所有的空格
            StrPro=StrPro.Trim().Replace(" ","");

            //空字符串
            if(StrPro.Length==0)
            {
                flag=1;
            }

            if (StrPro.IndexOf("==")>-1)
            {
                flag = 2;
            }

            //除了逻辑运算符,命题符号中有非字母字符
            string kk = StrPro.Replace("↔", "").Replace("﹁", "").Replace("∧", "").Replace("∨", "").Replace("=", "").Replace("→", "").Replace("(", "").Replace(")", "");
            if (!Regex.Match(kk,"^[A-Za-z]+$").Success)
            {              
                flag=3;
            }

            //合式公式中"(",")"数量相等
            if(StrPro.IndexOf("(")>-1&&StrPro.IndexOf(")")>-1)
            {
                int ll = Regex.Matches(StrPro, @"\(").Count;
                int mm=Regex.Matches(StrPro, @"\)").Count;

                if (Regex.Matches(StrPro, @"\(").Count!= Regex.Matches(StrPro, @"\)").Count)
                {
                    flag = 4;
                }
            }

            //合式公式中在最小运算单元中不存在&&,||并存的模糊定义
            string[] stringSplit = StrPro.Split(new char[] { '(' ,')'},StringSplitOptions.None);
            foreach(string item in stringSplit)
            {
                if(item.IndexOf("&&")>-1&&item.IndexOf("||")>-1)
                {                   
                    flag=5;         
                }
                else
                    continue;               
            }                   
            return flag;
        }

        /// <summary>
        /// 对逻辑运算中的等价,非,合取,析取符号进行替换
        /// </summary>
        /// <param name="StrPro"></param>
        /// <returns></returns>
        private static string SymbolRepalce(string StrPro)
        {

            StrPro = StrPro.Replace("↔", "==").Replace("﹁", "!").Replace("∧", "&&").Replace("∨", "||").Replace("=", "==");

            return StrPro;

        }

        /// <summary>
        /// 逻辑运算符蕴含→,比较特殊,需要通过之前完备性证明的一个命题进行形式转换
        /// </summary>
        /// <param name="StrPro"></param>
        /// <returns></returns>
        private  static string Formalize(string StrPro)
        {

            string strP="";
            int k = StrPro.IndexOf("→");
            string strArrF=StrPro.Substring(0,k);
            string strArrS = StrPro.Substring(k + 1);
            strP="!("+strArrF+")"+"||("+strArrS+")";
            int m = strP.IndexOf("→");
            while (m > -1)
            {
                Formalize(strP);  
            }
            return strP;
        }

        /// <summary>
        /// 取出所有命题符号
        /// </summary>
        /// <param name="StrPro"></param>
        /// <returns></returns>
        private static List<string> DefineBool(string StrPro)
        {
            string[] stringSplit = StrPro.Split(new string[] { "(" ,")","!","||","&&","=="},StringSplitOptions.None);

            List<string> strNew=new List<string>();

            foreach(string item in stringSplit)
            {
                if(item!="")
                {
                    strNew.Add(item);
                }
            }
            return strNew = strNew.AsEnumerable().Distinct().ToList();
        }   

    }
}

你可能感兴趣的:(命题逻辑,逻辑运算器,自动证明,逻辑证明)