コード例 #1
0
ファイル: ReverseChain.cs プロジェクト: asdanilenk/Exp1
 private double Defuz(Parameter parameter, int level)
 {
     _log.Add("Defuzzing variable:" + parameter.ParamName, level);
     Dictionary<Term,double> termValues = _fuzparamValues[parameter];
     string function = null;
     foreach (var termValue in termValues)
     {
         string localfunction = String.Format("min({0};{1})", termValue.Value.ToString(), termValue.Key.TermFunction);
         if (String.IsNullOrEmpty(function))
             function = localfunction;
         else
             function = String.Format("max({0};{1})", function, localfunction);
     }
     _log.Add("Compiled function: " + function, level);
     Parser parser = new Parser();
     parser.Parse(function, new List<string> {"x"});
     int left = parameter.termGroup.Terms[0].LeftRange;
     int right = parameter.termGroup.Terms[0].RightRange;
     double max = double.MinValue;
     double x = left;
     for (double i = left; i < right; i += ((double) right - left)/1000)
     {
         double value = parser.Calculate(new Dictionary<string, double> {{"x", i}});
         if (max<value)
         {
             max = value;
             x = i;
         }
     }
     _log.Add("Max value on x is: " + x, level);
     return x;
 }
コード例 #2
0
ファイル: ReverseChain.cs プロジェクト: asdanilenk/Exp1
        private bool ReccurentSearch(Parameter needed, int level)
        {
            _log.Add("Searching for " + needed.ParamName + " :", level);
            List<Rule> goodrules = _rules.FindAll(r => r.Result.ParamId == needed.ParamId);
            _log.Add("Rules found: " + goodrules.Count, level);
            if (goodrules.Count == 0 || goodrules.All(rule => rule.Conditions.Exists(cond => cond.Parameter.ParamId == needed.ParamId)))
            {
                return AskQuestion(needed, level);
            }

            var fuzzyTermValues = new Dictionary<Term, double>();
            foreach (Rule rule in goodrules)
            {
                _log.Add("Processing rule:" + rule, level);
                bool ruleOk = true;
                double rulefuzzys = 1;
                foreach (Condition condition in rule.Conditions.Where(cond => cond.Parameter.ParamType != ParamType.PFuzzy))
                {
                    _log.Add("Processing condition:" + condition, level);
                    Parameter p = _parameters.First(a => a.ParamId == condition.Parameter.ParamId);
                    if (_paramValues[p] == null)
                        if (ReccurentSearch(p, level + 1) == false)
                            return false;
                    if (!CheckCondition(condition))
                    {
                        _log.Add("Condition failed", level);
                        ruleOk = false;
                    }
                    else
                    {
                        _log.Add("Condition passed", level);
                    }
                }
                if (ruleOk)
                    foreach (Condition condition in rule.Conditions.Where(cond => cond.Parameter.ParamType == ParamType.PFuzzy))
                    {
                        _log.Add("Processing Fuzzy condition:" + condition, level);
                        Parameter p = _parameters.First(a => a.ParamId == condition.Parameter.ParamId);
                        if (_paramValues[p] == null)
                            if (ReccurentSearch(p, level + 1) == false)
                                return false;
                        if ((condition.Value is CreditParameter && (condition.Value as CreditParameter).ParamType != ParamType.PFuzzy) ||
                            condition.Value is double)
                        {
                            bool result = CheckCondition(condition);
                            ruleOk = result && ruleOk;
                            _log.Add("Fuzzy condition is not Fuzzy really. Result is " + result, level);
                        }
                        else
                        {
                            double result = CheckFuzzyCondition(condition);
                            rulefuzzys = Math.Min(rulefuzzys, result);
                            _log.Add("Fuzzy condition returned probability " + result, level);
                        }
                    }
                _log.Add("Finished processing conditions", level);

                if (ruleOk)
                {
                    _rules.Remove(rule);
                    Parameter p = _parameters.First(a => a.ParamId == rule.Result.ParamId);
                    _log.Add("Calculating result parameter " + rule.Result.ParamName + " using function " + rule.ResultValue, level);
                    if (p.ParamType == ParamType.PDouble ||
                        (p.ParamType == ParamType.PFuzzy && !p.termGroup.Terms.Exists(term => term.TermName == rule.ResultValue)))
                    {
                        var parser = new Parser();
                        List<string> vars = rule.ResultValue.Split(new[] {'-', '+', '/', '*', ')', '('}).ToList().ConvertAll(s => s.Trim());
                        foreach (string var in vars)
                        {
                            Parameter par = _parameters.Find(f => f.ParamName == var);
                            if (par != null && _paramValues[par] == null)
                                if (ReccurentSearch(par, level + 1) == false)
                                    return false;
                        }
                        List<CreditParameter> allParameters = _parameters.Cast<CreditParameter>().ToList();
                        allParameters.AddRange(_creditParam.Keys);
                        //localparameters now contains all parameters and creditparameters
                        List<string> parameterNames = allParameters.ConvertAll(a => a.ParamName);
                        try
                        {
                            parser.Parse(rule.ResultValue, parameterNames);
                        }
                        catch (Exception e)
                        {
                            MessageBox.Show(e.Message);
                            return false;
                        }

                        Dictionary<string, double> allParametersValues = _paramValues.ToValueList();
                        foreach (var crp in _creditParam.Where(crp => crp.Key.ParamType == ParamType.PDouble))
                            allParametersValues.Add(crp.Key.ParamName, double.Parse(crp.Value));
                        try
                        {
                            _paramValues[p] = parser.Calculate(allParametersValues);
                            if (p.ParamType == ParamType.PFuzzy)
                                CalculateTermValues(p, level);
                        }
                        catch (Exception e)
                        {
                            MessageBox.Show(e.Message);
                            return false;
                        }
                        _log.Add("Rule passed => " + p.ParamName + "=" + _paramValues[p], level);
                        return true;
                    }
                    if (p.ParamType == ParamType.PBool && _creditParam.Keys.ToList().Exists(par => par.ParamName == rule.ResultValue))
                    {
                        _paramValues[p] = _creditParam.First(par => par.Key.ParamName == rule.ResultValue).Value;
                        _log.Add("Rule passed => " + p.ParamName + "=" + _paramValues[p], level);
                        return true;
                    }
                    if (p.ParamType == ParamType.PFuzzy)
                    {
                        Term t = p.termGroup.Terms.First(term => term.TermName == rule.ResultValue);
                        if (fuzzyTermValues.Keys.ToList().Exists(term => term.TermName == t.TermName))
                            fuzzyTermValues[t] = Math.Max(rulefuzzys, fuzzyTermValues[t]);
                        else
                            fuzzyTermValues[t] = rulefuzzys;
                        _log.Add("Rule passed", level);
                    }
                    //for PString
                    else
                    {
                        _paramValues[p] = rule.ResultValue;
                        _log.Add("Rule passed => " + p.ParamName + "=" + _paramValues[p], level);
                        return true;
                    }
                }
                else
                    _log.Add("Rule failed", level);
            }
            if (needed.ParamType == ParamType.PFuzzy && fuzzyTermValues.Count()>0)
            {
                Parameter p = _parameters.First(a => a.ParamId == needed.ParamId);
                _fuzparamValues[p] = fuzzyTermValues;
                _paramValues[p] = Defuz(p, level);
                return true;
            }

            return AskQuestion(needed, level);
        }
コード例 #3
0
ファイル: ReverseChain.cs プロジェクト: asdanilenk/Exp1
 private void CalculateTermValues(Parameter needed, int level)
 {
     var dict = new Dictionary<Term, double>();
     foreach (Term term in needed.termGroup.Terms)
     {
         Parser parser = new Parser();
         parser.Parse(term.TermFunction, new List<string> {"x"});
         double value;
         if (_paramValues[needed] is double)
             value = (double) _paramValues[needed];
         else
             value = double.Parse(_paramValues[needed].ToString());
         if (value > term.RightRange)
             value = term.RightRange;
         if (value < term.LeftRange)
             value = term.LeftRange;
         dict[term] = parser.Calculate(new Dictionary<string, double> {{"x", value}});
         _log.Add("Term value for " + term.TermName + " : " + dict[term], level + 1);
     }
     _fuzparamValues[needed] = dict;
 }