. В принципе для понимания предыдущий пост можно не читать.
Хочется реалзиовать логические услвия.
Так вот в языке программирования как ни странно логические условия уже есть
if(a && b .... ((()))....(())
Элементарными условиями я могу сделать классы с интерфейсом IUslovie в котором есть метод Check() возвращающий true или false, короче сделать чтобы a, b (см. пример кода) были реалзованы проблем нет . Проблема в том что мне надо как то хранить все то что записано в скобке.
Идеальным в псеводкоде могу изобразить для себя следующий вариант:
if(DataBase.GiveMeNeededUslovie())
Action.DoIt();
Вот если бы в БД можно было сохраить прям в текстовом виде строку
a && b || (c && !d) (в общем все изыски и прелести условий языка программирования)
а потом медод DataBase.GiveMeNeededUslovie эту строку читал и проверил подставив в if, то было всё классно.
Вопрос: как это релизовать?
З.Ы.: для тех кто читал предыдущий пост: а картинки потом из этой строки распарсив можно нарисовать
Всем спасибо, простите за сумбур!
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: (де)Сереалзиация логичесого условия языка программирован
Здравствуйте, Time, Вы писали:
T>Всем спасибо, простите за сумбур!
Вот с сумбуром перебор, приходится угадывать что требуется. Представить выражение в виде дерева и научить узлы сериализоваться рекурсивно вызывая сериализацию нижележащих выражений — что-то такое? Тогда что не ясно?
... <<np: silent>>
Re: (де)Сереалзиация логичесого условия языка программирован
Здравствуйте, Time, Вы писали:
T> Элементарными условиями я могу сделать классы с интерфейсом IUslovie в котором есть метод Check() возвращающий true или false, короче сделать чтобы a, b (см. пример кода) были реалзованы проблем нет . Проблема в том что мне надо как то хранить все то что записано в скобке.
Нужно сделать фабрику, которая будет создавать новый объект IUslovie, создавая его из двух старых и операции (и/или/что-тебе-ещё-понадобится). Сереализовать такое проще всего в обратной польской записи.
Делай что должно, и будь что будет
Re: (де)Сереалзиация логичесого условия языка программирован
public interface IBasePredicate
{
}
public interface IBinary<T>:IBasePredicate
{
bool Compare(T x);
}
public interface ILogical<T> : IBasePredicate where T : IComparable<T>
{
List<FormulaCalculate<T>> Calculations{get;}
IEnumerable<T> Execute(IEnumerable<T> source);
}
[Serializable]
public class FormulaCalculate<T> where T:IComparable<T>
{
[Serializable]
public class EqualFilter<V>:IBinary<V> where V:IComparable<V>
{
V _compareValue;
public EqualFilter(V compareValue)
{
_compareValue = compareValue;
}
public bool Compare(V x)
{
return (_compareValue.CompareTo(x)==0);
}
}
[Serializable]
public class OrExecuter<V>:ILogical<V> where V:IComparable<V>
{
List<FormulaCalculate<V>> FormulaCalculate=new List<FormulaCalculate<V>>();
public List<FormulaCalculate<V>> Calculations
{
get{
return FormulaCalculate;
}
}
public IEnumerable<V> Execute(IEnumerable<V> source)
{
List<V> result=new List<V>();
Dictionary<V, int> union=new Dictionary<V,int>();
foreach(FormulaCalculate<V> calc in Calculations)
{
IEnumerable<V> calculated=calc.Execute(source);
foreach(V t in calculated)
if (!union.ContainsKey(t))
{
union.Add(t, 0);
result.Add(t);
}
}
return result;
}
}
private List<IBasePredicate> _predicates = new List<IBasePredicate>();
public List<IBasePredicate> Predicates { get { return _predicates; } }
private List<T> ExecuteBinary(IEnumerable<T> source, IBinary<T> predicate)
{
return ((List<T>)source).FindAll(predicate.Compare);
}
public IEnumerable<T> Execute(IEnumerable<T> source)
{
IEnumerable<T> valuesCollection = new List<T>();
foreach (IBasePredicate obj in Predicates)
{
if (obj is IBinary<T>) valuesCollection = ExecuteBinary(valuesCollection, obj as IBinary<T>);
else
if (obj is ILogical<T>) valuesCollection = (obj as ILogical<T>).Execute(valuesCollection);
}
return valuesCollection;
}
public FormulaCalculate<T> Equal(T x)
{
Predicates.Add(new EqualFilter<T>(x));
return this;
}
public FormulaCalculate<T> Or(FormulaCalculate<T> elem1, FormulaCalculate<T> elem2)
{
OrExecuter<T> orExecuter=new OrExecuter<T>();
orExecuter.Calculations.Add(elem1);
orExecuter.Calculations.Add(elem2);
Predicates.Add(orExecuter);
return this;
}
// ....
}
Здесь идет фильтрация коллекции, но можешь изменить на то, что тебе нужно и добавить различные условия.
Использование:
int[] a={10,20,30}
FormulaCalculate<int> dest =
new FormulaCalculate<int>().Or(
new FormulaCalculate<int>().Equal(10),
new FormulaCalculate<int>().Equal(20));
IEnumerable<int> l=dest.Execute(list);
Объект сериализуемый. Если нужно сериализовать в xml — то легко дописать.
Re: (де)Сереалзиация логичесого условия языка программирован
Возможно, в твоем случае удобным окажется применение IronPython.
Там можно задать словарь локальных переменных (перечислить, что a = 3; b = 7.3; c = true).
После в контексте заданных локальных переменных вычислить значение выражения.
Я так делал почти год назад.
Писал что-то вроде
using IronPython;
// ... код, код, код
PythonEngine evaluator = new PythonEngine();
Dictionary<string, object> localVariables = new Dictionary<string, object>();
localVariables["a"] = 3;
localVariables["b"] = 7.3;
bool result = (bool)evaluator.Evaluate("a + b > 10", localVariables);
Можно также применить компилятор шарпа или любого другого подходящего языка, но тогда выражение придется оборачивать методом, а метод — классом, компилить код в сборку, загружать сборку и через рефлекшен дергать сгенеренный метод.
Хотя может быть можно и без этого .