4

C#: 次のような文字列変数があります。

 string a = "(true and true) or (true or false)";

これは何でもかまいません。次のように、より複雑になる可能性があります。

 string b = "((true and false) or (true or false) and not (true and false)) and false";

私が知っているのは、それが正しいということだけです。この式を「評価」できないということはあり得ません。

これをどうにかして評価する方法はありますか?その文字列の結果(結果)だけを知りたいです。これは、この文字列の代わりに「true」または「false」が必要であることを意味します。

これを行う解析メソッドを作成し、最終的な値を取得するまで文字列を段階的に削減できると思いますが、より良いアプローチがあるかどうか疑問に思っていました。

4

4 に答える 4

10

Rob のコメントを拡張すると、ランタイム コンパイルを C# 4.0dynamicサポートと組み合わせて使用​​でき、次のようなことができます。

var expression = "(true and false) or (true or false)";

var helper = "" + 
    "using System; " + 
    "public class Expression {{ public bool Eval() {{ return {0}; }} }}";

var replaced = expression.Replace("and", "&&").Replace("or", "||");

var references = new string[] { "System.dll" };
var parameters = new CompilerParameters(references, "Test.dll");
var compiler = new CSharpCodeProvider();


var results = compiler.CompileAssemblyFromSource(
    parameters, 
    String.Format(helper, replaced));

dynamic exp = Activator.CreateInstance(
    results.CompiledAssembly.GetType("Expression"));

Console.WriteLine(exp.Eval());
于 2011-06-07T15:07:56.457 に答える
7

もしかしてこういうこと?

string previous = string.Empty;
while (b != previous) 
{
     previous = b;
     b = b.Replace("true and false", "false");
     b = b.Replace("true and true", "true");
     b = b.Replace("false and true", "false");
     b = b.Replace("false and false", "false");
     b = b.Replace("false or false", "false");
     b = b.Replace("true or false", "true");
     b = b.Replace("true or true", "true");
     b = b.Replace("false or true", "true");
     b = b.Replace("(false)", "false");
     b = b.Replace("(true)", "true");
     b = b.Replace("not false", "true");
     b = b.Replace("not true", "false");
 }

仕様では、次のようなあいまいな定式化が許可されていることに注意してください。

"false and false or true"
"false and true or true"

これらの式は両方とも、andが最初に評価される場合は「true」、 orが最初に評価される場合は「false」です。したがって、すべてのレベルで括弧を必要とする方がよいでしょう。左から右への評価を要求することも別のオプションですが、それではコードが少し複雑になります。

このスタイルの問題に対するこのスタイルの解法に反対するかもしれない人は、一部の数学者が、すべての数学がこの種の記号操作に還元される可能性があると信じていることを思い出してください。ラッセルとホワイトヘッドの『プリンキピア・マセマティカ』に対する主な批判の 1 つは、公式にあまりにも多くの意味を埋め込んでいるということだと言われています。

于 2011-06-07T14:42:50.620 に答える
2

構文解析が最善の策です。タイプミスをチェックする必要がある場合、それは少し難しくなります。

于 2011-06-07T14:40:35.133 に答える
-1

C#には、このようなステートメントを実行して最終結果を取得できるEvalメソッドなどがありません。私が何かを見逃していない限り、あなたはそのように解析して減らす必要があります。

于 2011-06-07T14:40:27.907 に答える