Esempio n. 1
0
        static private void BuildLexemsList <VariableType, ValueType>(VariableType var, bool input, Dictionary <string, Lexem> lexems)
            where VariableType : class, INamedVariable
            where ValueType : class, INamedValue
        {
            VarLexem <VariableType> varLexem = new VarLexem <VariableType>(var, input);

            lexems.Add(varLexem.Text, varLexem);
            foreach (ValueType term in var.Values)
            {
                TermLexem <ValueType> termLexem = new TermLexem <ValueType>(term, input);

                Lexem foundLexem = null;
                if (!lexems.TryGetValue(termLexem.Text, out foundLexem))
                {
                    //
                    // There are no lexems with the same text. Just insert new lexem.
                    //
                    lexems.Add(termLexem.Text, termLexem);
                }
                else
                {
                    if (foundLexem is IAltLexem)
                    {
                        //
                        // There can be more than one terms with the same name.
                        // TODO: But only if they belong to defferent variables.
                        //
                        IAltLexem foundTermLexem = (IAltLexem)foundLexem;
                        while (foundTermLexem.Alternative != null)
                        {
                            foundTermLexem = foundTermLexem.Alternative;
                        }
                        foundTermLexem.Alternative = termLexem;
                    }
                    else
                    {
                        //
                        // Only terms of different vatiables can have the same name
                        //
                        throw new System.Exception(string.Format("Found more than one lexems with the same name: {0}", termLexem.Text));
                    }
                }
            }
        }
Esempio n. 2
0
        static private void BuildLexemsList <VariableType, ValueType>(VariableType var, bool input, Dictionary <string, Lexem> lexems)
            where VariableType : class, INamedVariable
            where ValueType : class, INamedValue
        {
            VarLexem <VariableType> varLexem = new VarLexem <VariableType>(var, input);

            lexems.Add(varLexem.Text, varLexem);
            foreach (ValueType term in var.Values)
            {
                TermLexem <ValueType> termLexem = new TermLexem <ValueType>(term, input);

                Lexem foundLexem = null;
                if (!lexems.TryGetValue(termLexem.Text, out foundLexem))
                {
                    //
                    // Нет лексем с похожим текстом. Только добавление новых лексем
                    //
                    lexems.Add(termLexem.Text, termLexem);
                }
                else
                {
                    if (foundLexem is IAltLexem)
                    {
                        //
                        // Там может быть более одного условия с тем же именем.
                        // TODO: Но только если они принадлежат к разным переменных.
                        //
                        IAltLexem foundTermLexem = (IAltLexem)foundLexem;
                        while (foundTermLexem.Alternative != null)
                        {
                            foundTermLexem = foundTermLexem.Alternative;
                        }
                        foundTermLexem.Alternative = termLexem;
                    }
                    else
                    {
                        //
                        // Только термы различных переменных могут иметь похожие имена
                        //
                        throw new System.Exception(string.Format("Найден более чем одна лексема с похожим именем: {0}", termLexem.Text));
                    }
                }
            }
        }
Esempio n. 3
0
        static private SingleCondition <VariableType, ValueType> ParseConclusion <VariableType, ValueType>(List <IExpression> conditionExpression, List <VariableType> output, Dictionary <string, Lexem> lexems)
            where VariableType : class, INamedVariable
            where ValueType : class, INamedValue
        {
            List <IExpression> copyExpression = conditionExpression.GetRange(0, conditionExpression.Count);

            //
            // Remove extra brackets
            //
            while (
                copyExpression.Count >= 2 &&
                (copyExpression[0] == lexems["("] && copyExpression[conditionExpression.Count - 1] == lexems[")"]))
            {
                copyExpression = copyExpression.GetRange(1, copyExpression.Count - 2);
            }

            if (copyExpression.Count != 3)
            {
                throw new Exception("Conclusion part of the rule should be in form: 'variable is term'");
            }

            //
            // Parse variable
            //
            Lexem exprVariable = (Lexem)copyExpression[0];

            if (!(exprVariable is VarLexem <VariableType>))
            {
                throw new Exception(string.Format("Wrong identifier '{0}' in conclusion part of the rule.", exprVariable.Text));
            }

            VarLexem <VariableType> varLexem = (VarLexem <VariableType>)exprVariable;

            if (varLexem.Input == true)
            {
                throw new Exception("The variable in conclusion part must be an output variable.");
            }

            //
            // Parse 'is' lexem
            //
            Lexem exprIs = (Lexem)copyExpression[1];

            if (exprIs != lexems["is"])
            {
                throw new Exception(string.Format("'is' keyword must go after {0} identifier.", varLexem.Text));
            }

            //
            // Parse term
            //
            Lexem exprTerm = (Lexem)copyExpression[2];

            if (!(exprTerm is IAltLexem))
            {
                throw new Exception(string.Format("Wrong identifier '{0}' in conclusion part of the rule.", exprTerm.Text));
            }

            IAltLexem             altLexem  = (IAltLexem)exprTerm;
            TermLexem <ValueType> termLexem = null;

            do
            {
                if (!(altLexem is TermLexem <ValueType>))
                {
                    continue;
                }

                termLexem = (TermLexem <ValueType>)altLexem;
                if (!varLexem.Var.Values.Contains(termLexem.Term))
                {
                    termLexem = null;
                    continue;
                }
            }while ((altLexem = altLexem.Alternative) != null && termLexem == null);

            if (termLexem == null)
            {
                throw new Exception(string.Format("Wrong identifier '{0}' in conclusion part of the rule.", exprTerm.Text));
            }

            //
            // Return fuzzy rule's conclusion
            //
            return(new SingleCondition <VariableType, ValueType>(varLexem.Var, termLexem.Term, false));
        }
Esempio n. 4
0
        static private List <IExpression> ExtractSingleCondidtions(List <IExpression> conditionExpression, List <FuzzyVariable> input, Dictionary <string, Lexem> lexems)
        {
            List <IExpression> copyExpressions = conditionExpression.GetRange(0, conditionExpression.Count);
            List <IExpression> expressions     = new List <IExpression>();

            while (copyExpressions.Count > 0)
            {
                if (copyExpressions[0] is VarLexem <FuzzyVariable> )
                {
                    //
                    // Parse variable
                    //
                    VarLexem <FuzzyVariable> varLexem = (VarLexem <FuzzyVariable>)copyExpressions[0];
                    if (copyExpressions.Count < 3)
                    {
                        throw new Exception(string.Format("Condition strated with '{0}' is incorrect.", varLexem.Text));
                    }

                    if (varLexem.Input == false)
                    {
                        throw new Exception("The variable in condition part must be an input variable.");
                    }

                    //
                    // Parse 'is' lexem
                    //
                    Lexem exprIs = (Lexem)copyExpressions[1];
                    if (exprIs != lexems["is"])
                    {
                        throw new Exception(string.Format("'is' keyword must go after {0} identifier.", varLexem.Text));
                    }


                    //
                    // Parse 'not' lexem (if exists)
                    //
                    int  cur = 2;
                    bool not = false;
                    if (copyExpressions[cur] == lexems["not"])
                    {
                        not = true;
                        cur++;

                        if (copyExpressions.Count <= cur)
                        {
                            throw new Exception("Error at 'not' in condition part of the rule.");
                        }
                    }

                    //"slightly"
                    //"somewhat"
                    //"very"
                    //"extremely"

                    //
                    // Parse hedge modifier (if exists)
                    //
                    HedgeType hedge = HedgeType.None;
                    if (copyExpressions[cur] == lexems["slightly"])
                    {
                        hedge = HedgeType.Slightly;
                    }
                    else if (copyExpressions[cur] == lexems["somewhat"])
                    {
                        hedge = HedgeType.Somewhat;
                    }
                    else if (copyExpressions[cur] == lexems["very"])
                    {
                        hedge = HedgeType.Very;
                    }
                    else if (copyExpressions[cur] == lexems["extremely"])
                    {
                        hedge = HedgeType.Extremely;
                    }

                    if (hedge != HedgeType.None)
                    {
                        cur++;

                        if (copyExpressions.Count <= cur)
                        {
                            throw new Exception(string.Format("Error at '{0}' in condition part of the rule.", hedge.ToString().ToLower()));
                        }
                    }

                    //
                    // Parse term
                    //
                    Lexem exprTerm = (Lexem)copyExpressions[cur];
                    if (!(exprTerm is IAltLexem))
                    {
                        throw new Exception(string.Format("Wrong identifier '{0}' in conditional part of the rule.", exprTerm.Text));
                    }

                    IAltLexem             altLexem  = (IAltLexem)exprTerm;
                    TermLexem <FuzzyTerm> termLexem = null;
                    do
                    {
                        if (!(altLexem is TermLexem <FuzzyTerm>))
                        {
                            continue;
                        }

                        termLexem = (TermLexem <FuzzyTerm>)altLexem;
                        if (!varLexem.Var.Values.Contains(termLexem.Term))
                        {
                            termLexem = null;
                            continue;
                        }
                    }while ((altLexem = altLexem.Alternative) != null && termLexem == null);

                    if (termLexem == null)
                    {
                        throw new Exception(string.Format("Wrong identifier '{0}' in conditional part of the rule.", exprTerm.Text));
                    }

                    //
                    // Add new condition expression
                    //
                    FuzzyCondition condition = new FuzzyCondition(varLexem.Var, termLexem.Term, not, hedge);
                    expressions.Add(new ConditionExpression(copyExpressions.GetRange(0, cur + 1), condition));
                    copyExpressions.RemoveRange(0, cur + 1);
                }
                else
                {
                    IExpression expr = copyExpressions[0];
                    if (expr == lexems["and"] ||
                        expr == lexems["or"] ||
                        expr == lexems["("] ||
                        expr == lexems[")"])
                    {
                        expressions.Add(expr);
                        copyExpressions.RemoveAt(0);
                    }
                    else
                    {
                        Lexem unknownLexem = (Lexem)expr;
                        throw new Exception(string.Format("Lexem '{0}' found at the wrong place in condition part of the rule.", unknownLexem.Text));
                    }
                }
            }

            return(expressions);
        }
Esempio n. 5
0
        static private SingleCondition <VariableType, ValueType> ParseConclusion <VariableType, ValueType>(List <IExpression> conditionExpression, List <VariableType> output, Dictionary <string, Lexem> lexems)
            where VariableType : class, INamedVariable
            where ValueType : class, INamedValue
        {
            List <IExpression> copyExpression = conditionExpression.GetRange(0, conditionExpression.Count);

            //
            // Удаление лишних скобок
            //
            while (
                copyExpression.Count >= 2 &&
                (copyExpression[0] == lexems["("] && copyExpression[conditionExpression.Count - 1] == lexems[")"]))
            {
                copyExpression = copyExpression.GetRange(1, copyExpression.Count - 2);
            }

            if (copyExpression.Count != 3)
            {
                throw new Exception("Вывод часть правила должны быть в форме: 'переменная есть терм'");
            }

            //
            // Разбор переменной
            //
            Lexem exprVariable = (Lexem)copyExpression[0];

            if (!(exprVariable is VarLexem <VariableType>))
            {
                throw new Exception(string.Format("Неверный идентификатор '{0}' в состоянии части правила.", exprVariable.Text));
            }

            VarLexem <VariableType> varLexem = (VarLexem <VariableType>)exprVariable;

            if (varLexem.Input == true)
            {
                throw new Exception("Переменная в заключительной части должна быть выходной переменной.");
            }

            //
            // Разбор 'is' лексемы
            //
            Lexem exprIs = (Lexem)copyExpression[1];

            if (exprIs != lexems["is"])
            {
                throw new Exception(string.Format("'is' ключевое слово после {0} идентификатора.", varLexem.Text));
            }

            //
            // Parse term
            //
            Lexem exprTerm = (Lexem)copyExpression[2];

            if (!(exprTerm is IAltLexem))
            {
                throw new Exception(string.Format("Неверный идентификатор '{0}' в заключительной части правила.", exprTerm.Text));
            }

            IAltLexem             altLexem  = (IAltLexem)exprTerm;
            TermLexem <ValueType> termLexem = null;

            do
            {
                if (!(altLexem is TermLexem <ValueType>))
                {
                    continue;
                }

                termLexem = (TermLexem <ValueType>)altLexem;
                if (!varLexem.Var.Values.Contains(termLexem.Term))
                {
                    termLexem = null;
                    continue;
                }
            }while ((altLexem = altLexem.Alternative) != null && termLexem == null);

            if (termLexem == null)
            {
                throw new Exception(string.Format("Неверный идентификатор '{0}' в заключительной части правила.", exprTerm.Text));
            }

            //
            // Возвращение нечеткого правила заключения
            //
            return(new SingleCondition <VariableType, ValueType>(varLexem.Var, termLexem.Term, false));
        }
Esempio n. 6
0
        static private List <IExpression> ExtractSingleCondidtions(List <IExpression> conditionExpression, List <FuzzyVariable> input, Dictionary <string, Lexem> lexems)
        {
            List <IExpression> copyExpressions = conditionExpression.GetRange(0, conditionExpression.Count);
            List <IExpression> expressions     = new List <IExpression>();

            while (copyExpressions.Count > 0)
            {
                if (copyExpressions[0] is VarLexem <FuzzyVariable> )
                {
                    //
                    // Разбор переменной
                    //
                    VarLexem <FuzzyVariable> varLexem = (VarLexem <FuzzyVariable>)copyExpressions[0];
                    if (copyExpressions.Count < 3)
                    {
                        throw new Exception(string.Format("Состояние начинается с '{0}' не корректно.", varLexem.Text));
                    }

                    if (varLexem.Input == false)
                    {
                        throw new Exception("Переменная в состоянии должна быть входной переменной.");
                    }

                    //
                    // Разбор "is" лексемы
                    //
                    Lexem exprIs = (Lexem)copyExpressions[1];
                    if (exprIs != lexems["is"])
                    {
                        throw new Exception(string.Format("'is' ключевое слово должно идти после {0} идентификатора.", varLexem.Text));
                    }


                    //
                    // Разбор 'not' лексемы (если существует)
                    //
                    int  cur = 2;
                    bool not = false;
                    if (copyExpressions[cur] == lexems["not"])
                    {
                        not = true;
                        cur++;

                        if (copyExpressions.Count <= cur)
                        {
                            throw new Exception("Ошибка около 'not' в состоянии части правила.");
                        }
                    }

                    //"slightly"    - немного
                    //"somewhat"    - в некотором роде
                    //"very"        - очень
                    //"extremely"   - чрезвычайно

                    //
                    // Разбор hedge модификатора (если существует)
                    //
                    HedgeType hedge = HedgeType.None;
                    if (copyExpressions[cur] == lexems["slightly"])
                    {
                        hedge = HedgeType.Slightly;
                    }
                    else if (copyExpressions[cur] == lexems["somewhat"])
                    {
                        hedge = HedgeType.Somewhat;
                    }
                    else if (copyExpressions[cur] == lexems["very"])
                    {
                        hedge = HedgeType.Very;
                    }
                    else if (copyExpressions[cur] == lexems["extremely"])
                    {
                        hedge = HedgeType.Extremely;
                    }

                    if (hedge != HedgeType.None)
                    {
                        cur++;

                        if (copyExpressions.Count <= cur)
                        {
                            throw new Exception(string.Format("Ошибка около '{0}' в состоянии части правила.", hedge.ToString().ToLower()));
                        }
                    }

                    //
                    // Разбор терма
                    //
                    Lexem exprTerm = (Lexem)copyExpressions[cur];
                    if (!(exprTerm is IAltLexem))
                    {
                        throw new Exception(string.Format("Неверный идентификатор '{0}' в стостоянии части правила.", exprTerm.Text));
                    }
                    IAltLexem             altLexem  = (IAltLexem)exprTerm;
                    TermLexem <FuzzyTerm> termLexem = null;
                    do
                    {
                        if (!(altLexem is TermLexem <FuzzyTerm>))
                        {
                            continue;
                        }

                        termLexem = (TermLexem <FuzzyTerm>)altLexem;
                        if (!varLexem.Var.Values.Contains(termLexem.Term))
                        {
                            termLexem = null;
                            continue;
                        }
                    }while ((altLexem = altLexem.Alternative) != null && termLexem == null);

                    if (termLexem == null)
                    {
                        throw new Exception(string.Format("Неверный идентификатор '{0}' в стостоянии части правила.", exprTerm.Text));
                    }

                    //
                    // Добавление нового выражения состояния
                    //
                    FuzzyCondition condition = new FuzzyCondition(varLexem.Var, termLexem.Term, not, hedge);
                    expressions.Add(new ConditionExpression(copyExpressions.GetRange(0, cur + 1), condition));
                    copyExpressions.RemoveRange(0, cur + 1);
                }
                else
                {
                    IExpression expr = copyExpressions[0];
                    if (expr == lexems["and"] ||
                        expr == lexems["or"] ||
                        expr == lexems["("] ||
                        expr == lexems[")"])
                    {
                        expressions.Add(expr);
                        copyExpressions.RemoveAt(0);
                    }
                    else
                    {
                        Lexem unknownLexem = (Lexem)expr;
                        throw new Exception(string.Format("Лексема  '{0}' найдена в ошибочном месте в состоянии части правила.", unknownLexem.Text));
                    }
                }
            }

            return(expressions);
        }