Imports System.Collections.Generic
Imports System.Math
Public Class หน้าฮี_Calculator
Private Delegate Function DelegateFormula(ByVal m As Double, ByVal n As Double) As Double
Private Shared Formula As New Dictionary(Of String, DelegateFormula)() From {{"+", Function(m, n) m + n},
{"-", Function(m, n) m - n},
{"*", Function(m, n) m * n},
{"/", Function(m, n) m / n}
}
''' <summary>
''' Example : Dim ret = Calculate(12.50, 10.00, "-")
''' result = 2.50
''' </summary>
Public Shared Function Calculate(ByVal a As Double, b As Double, Optional ByVal Oper As String = "+") As Double
Dim retValue As Double = 0.0
If (("+-*/").Contains(Oper)) AndAlso (Not (Oper = "/" AndAlso b = 0)) Then
retValue = Formula(Oper).Invoke(a, b)
End If
Return retValue
End Function
End Class
Public Class DHBConversionTable 'Dec, Hex, Bin
Public Property Dec As String
Public Property Hex As String
Public Property Bin As String
Public Property Description As String
Public Shared Function GetConversionTable(Optional ByVal n As Integer = 255) As List(Of DHBConversionTable)
Dim lstDHB As New List(Of DHBConversionTable)
n.ToString("N0").AsParallel.ForAll(Sub(x)
Dim y As Integer = Char.GetNumericValue(x)
Dim z = Char.IsLetterOrDigit(x)
End Sub)
For i As Integer = 0 To 255
lstDHB.Add(New DHBConversionTable() With {.Dec = i.ToString("D2"),
.Hex = i.ToString("X2"),
.Bin = Convert.ToString(i, 2).PadLeft(8, "0"c)
})
Next
Return lstDHB
End Function
End Class
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace InfixNotationConverter
{
public static class ExtensionMethods
{
public static Queue<T> ToQueue<T>(this List<T> items)
{
Queue<T> queue = new Queue<T>();
items.ForEach(item => queue.Enqueue(item));
return queue;
}
public static Stack<T> ToStack<T>(this List<T> items)
{
Stack<T> stack = new Stack<T>();
items.ForEach(item => stack.Push(item));
return stack;
}
}
}
Token.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace InfixNotationConverter
{
public class Token
{
public string Element { get; set; }
public double Value { get; set; }
public ElementType Type { get; set; }
}
public enum ElementType
{
Operand,
Operator
}
}
Date :
2016-02-10 09:06:33
By :
ห้ามตอบเกินวันละ 2 กระทู้
No. 12
Guest
InfixNotation.cs
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
namespace InfixNotationConverter
{
public class InfixNotation : List<Token>
{
private string _input;
private string _expression;
private bool _isValid;
public InfixNotation()
{
this._input = string.Empty;
this._expression = string.Empty;
this._isValid = false;
}
public InfixNotation(string input)
{
this.Input = input;
}
public string Input
{
set
{
this._input = value;
List<Token> tokens = this.ToTokens(this._input);
this._isValid = this.Validate(tokens);
if (this._isValid)
{
this.AddRange(this.ToInfix(tokens));
this._expression = this.Select(t => (t.Type == ElementType.Operand) ? t.Value.ToString() : t.Element).Aggregate((current, next) => current + next);
}
else
{
this._expression = string.Empty;
}
}
get
{
return this._input;
}
}
public string Expression
{
set
{
this._expression = value;
}
get
{
return this._expression;
}
}
public bool IsValid
{
get
{
return this._isValid;
}
}
public override string ToString()
{
return (this.Count > 0) ? this.Select(t => t.Element).Aggregate((current, next) => current + next) : string.Empty;
}
private List<Token> ToInfix(List<Token> input)
{
List<Token> infix = new List<Token>();
Dictionary<string, double> variables = new Dictionary<string, double>();
input.Where(e => e.Type == ElementType.Operand).GroupBy(e => Convert.ToDouble(e.Element)).Select(g => g.Key).ToList().ForEach(g =>
{
string key = (variables.Count > 25) ? "X" + (variables.Count - 25).ToString() : ((char)('A' + variables.Count)).ToString();
variables.Add(key, g);
});
foreach (Token token in input)
{
if (token.Type == ElementType.Operand)
{
KeyValuePair<string, double> variable = variables.Where(v => v.Value == Convert.ToDouble(token.Element)).First();
infix.Add(new Token() { Element = variable.Key, Value = variable.Value, Type = ElementType.Operand });
}
else
{
infix.Add(token);
}
}
return infix;
}
public PostfixNotation ToPostfix()
{
DataTable solution;
return this.ToPostfix(out solution);
}
public PostfixNotation ToPostfix(out DataTable solution)
{
solution = new DataTable();
solution.Columns.Add(new DataColumn("Index", typeof(string)));
solution.Columns.Add(new DataColumn("Infix", typeof(string)));
solution.Columns.Add(new DataColumn("Operator", typeof(string)));
solution.Columns.Add(new DataColumn("Postfix", typeof(string)));
Queue<Token> infix = this.ToQueue();
PostfixNotation postfix = new PostfixNotation();
Stack<Token> operators = new Stack<Token>();
int row = 0;
while (infix.Count > 0)
{
Token token = infix.Dequeue();
row++;
if (token.Type == ElementType.Operator)
{
if (token.Element == "(")
{
operators.Push(token);
}
else if (token.Element == ")")
{
if (operators.Count > 0)
{
while ((operators.Count > 0) ? operators.Peek().Element != "(" : false)
postfix.Add(operators.Pop());
if (operators.Count > 0)
operators.Pop();
}
}
else
{
if (operators.Count > 0)
{
while ((operators.Count > 0) ? (token.Element != "^") ? operators.Peek().Value >= token.Value : false : false)
postfix.Add(operators.Pop());
}
operators.Push(token);
}
}
else
{
postfix.Add(token);
}
this.AddDataRow("Postfix", solution, string.Format("{0}.", row), token.Element, this.PrintStack(operators), postfix.ToString());
}
if (operators.Count > 0)
{
string opr = string.Empty;
while (operators.Count > 0)
postfix.Add(operators.Pop());
this.AddDataRow("Postfix", solution, string.Format("{0}.", row + 1), string.Empty, this.PrintStack(operators), postfix.ToString());
}
return postfix;
}
public PrefixNotation ToPrefix()
{
DataTable solution;
return this.ToPrefix(out solution);
}
public PrefixNotation ToPrefix(out DataTable solution)
{
solution = new DataTable();
solution.Columns.Add(new DataColumn("Index", typeof(string)));
solution.Columns.Add(new DataColumn("Infix", typeof(string)));
solution.Columns.Add(new DataColumn("Operator", typeof(string)));
solution.Columns.Add(new DataColumn("Prefix", typeof(string)));
Stack<Token> infix = this.ToStack();
PrefixNotation prefix = new PrefixNotation();
Stack<Token> operators = new Stack<Token>();
int row = 0;
while (infix.Count > 0)
{
Token token = infix.Pop();
row++;
if (token.Type == ElementType.Operator)
{
if (token.Element == ")")
{
operators.Push(token);
}
else if (token.Element == "(")
{
if (operators.Count > 0)
{
while ((operators.Count > 0) ? operators.Peek().Element != ")" : false)
prefix.Insert(0, operators.Pop());
if (operators.Count > 0)
operators.Pop();
}
}
else
{
if (operators.Count > 0)
{
while ((operators.Count > 0) ? operators.Peek().Value >= token.Value : false)
prefix.Insert(0, operators.Pop());
}
operators.Push(token);
}
}
else
{
prefix.Insert(0, token);
}
this.AddDataRow("Prefix", solution, string.Format("{0}.", row), token.Element, this.PrintStack(operators), prefix.ToString());
}
if (operators.Count > 0)
{
string opr = string.Empty;
while (operators.Count > 0)
prefix.Insert(0, operators.Pop());
this.AddDataRow("Prefix", solution, string.Format("{0}.", row + 1), string.Empty, this.PrintStack(operators), prefix.ToString());
}
return prefix;
}
private List<Token> ToTokens(string input)
{
List<Token> output = new List<Token>();
string expression = input;
string number = string.Empty;
while (expression.Contains("()"))
expression = expression.Replace("()", string.Empty);
expression = Regex.Replace(expression, @"[0-9]\(", delegate(Match match)
{
return match.ToString().Substring(0, 1) + "*(";
});
expression = Regex.Replace(expression, @"\)[0-9]", delegate(Match match)
{
return ")*" + match.ToString().Substring(1, 1);
});
foreach (char c in expression.ToCharArray())
{
switch (c)
{
case '+':
case '-':
if (number != string.Empty)
{
output.Add(new Token() { Element = number, Value = 0, Type = ElementType.Operand });
output.Add(new Token() { Element = c.ToString(), Value = this.OperatorOrder(c.ToString()), Type = ElementType.Operator });
number = string.Empty;
}
else if (output.Count == 0)
{
number += c.ToString();
}
else if (output.Last().Element != ")")
{
number += c.ToString();
}
else
{
output.Add(new Token() { Element = c.ToString(), Value = this.OperatorOrder(c.ToString()), Type = ElementType.Operator });
}
break;
case '*':
case '/':
case '^':
case '(':
case ')':
if (number != string.Empty)
{
output.Add(new Token() { Element = number, Value = 0, Type = ElementType.Operand });
number = string.Empty;
}
output.Add(new Token() { Element = c.ToString(), Value = this.OperatorOrder(c.ToString()), Type = ElementType.Operator });
break;
default:
number += c.ToString();
break;
}
}
if (number != string.Empty)
output.Add(new Token() { Element = number, Value = 0, Type = ElementType.Operand });
int index = 1;
while (index > 0 && index < output.Count - 1)
{
string previous = output[index - 1].Element;
ElementType current = output[index].Type;
string next = output[index + 1].Element;
if (previous == "(" && current == ElementType.Operand && next == ")")
{
output.RemoveAt(index + 1);
output.RemoveAt(index - 1);
index--;
}
else
{
index++;
}
}
return output;
}
private bool Validate(List<Token> input)
{
bool isValide = false;
if (input.Count > 0)
{
int OpenBracket = input.Where(e => e.Element == "(").Count();
int CloseBracket = input.Where(e => e.Element == ")").Count();
int Operand = input.Where(e => e.Type == ElementType.Operand).Count();
bool result = true;
double tryDouble = 0.0;
input.Where(e => e.Type == ElementType.Operand).GroupBy(e => e.Element).Select(g => g.Key).ToList().ForEach(g => result &= double.TryParse(g, out tryDouble));
isValide = (OpenBracket == CloseBracket) && (Operand > 0) && result;
}
return isValide;
}
private double OperatorOrder(string op)
{
double value;
switch (op)
{
default: value = -1.0; break;
case "+": value = 1.0; break;
case "-": value = 1.0; break;
case "*": value = 2.0; break;
case "/": value = 2.0; break;
case "^": value = 3.0; break;
}
return value;
}
private string PrintStack(Stack<Token> stack)
{
return (stack.Count > 0) ? stack.ToList().Select(s => s.Element).Reverse().Aggregate((current, next) => current + next) : string.Empty;
}
private void AddDataRow(string name, DataTable dt, string index, string infix, string opr, string output)
{
DataRow dr = dt.NewRow();
dr.SetField<string>("Index", index);
dr.SetField<string>("Infix", infix);
dr.SetField<string>("Operator", opr);
dr.SetField<string>(name, output);
dt.Rows.Add(dr);
}
}
}
Date :
2016-02-10 09:07:43
By :
ห้ามตอบเกินวันละ 2 กระทู้
No. 13
Guest
PostfixNotation.cs
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace InfixNotationConverter
{
public class PostfixNotation : List<Token>
{
public override string ToString()
{
return (this.Count > 0) ? this.Select(t => t.Element).Aggregate((current, next) => current + next) : string.Empty;
}
public virtual bool IsSuccess(out string message)
{
Queue<Token> postfix = this.ToQueue();
Stack<double> variables = new Stack<double>();
bool isSuccess = true;
message = "Success";
while (postfix.Count > 0)
{
Token token = postfix.Dequeue();
if (token.Type == ElementType.Operator)
{
double x = 0.0;
double y = 0.0;
double result = 0.0;
if (variables.Count > 0)
{
x = variables.Pop();
if (variables.Count > 0)
{
y = variables.Pop();
}
else
{
isSuccess = false;
message = "Error: Syntax error.";
}
}
else
{
isSuccess = false;
message = "Error: Syntax error.";
}
switch (token.Element)
{
case "^": result = Math.Pow(y, x); break;
case "*": result = y * x; break;
case "/":
if (x != 0)
{
result = y / x;
}
else
{
isSuccess = false;
message = "Error: Devide by zero.";
}
break;
case "+": result = y + x; break;
case "-": result = y - x; break;
}
variables.Push(result);
}
else
{
variables.Push(token.Value);
}
}
return isSuccess;
}
public virtual double Calculate()
{
DataTable solution;
return Calculate(out solution);
}
public virtual double Calculate(out DataTable solution)
{
Queue<Token> postfix = this.ToQueue();
Stack<double> variables = new Stack<double>();
bool hasError = false;
string message = string.Empty;
int row = 0;
solution = new DataTable();
solution.Columns.Add(new DataColumn("Index", typeof(string)));
solution.Columns.Add(new DataColumn("Postfix", typeof(string)));
solution.Columns.Add(new DataColumn("Value", typeof(string)));
solution.Columns.Add(new DataColumn("Answer", typeof(string)));
while (postfix.Count > 0)
{
Token token = postfix.Dequeue();
row++;
if (token.Type == ElementType.Operator)
{
string calc = string.Empty;
double x = 0.0;
double y = 0.0;
double result = 0.0;
if (variables.Count > 0)
{
x = variables.Pop();
if (variables.Count > 0)
{
y = variables.Pop();
}
else
{
hasError = true;
message = "Error: Syntax error.";
}
}
else
{
hasError = true;
message = "Error: Syntax error.";
}
switch (token.Element)
{
case "^":
result = Math.Pow(y, x);
calc = (hasError) ? string.Empty : string.Format("{0}^{1}", y, x);
break;
case "*":
result = y * x;
calc = (hasError) ? string.Empty : string.Format("{0}*{1}", y, x);
break;
case "/":
if (x != 0)
{
result = y / x;
calc = (hasError) ? string.Empty : string.Format("{0}/{1}", y, x);
}
else
{
hasError = true;
message = "Error: Devide by zero.";
}
break;
case "+":
result = y + x;
calc = (hasError) ? string.Empty : string.Format("{0}+{1}", y, x);
break;
case "-":
result = y - x;
calc = (hasError) ? string.Empty : string.Format("{0}-{1}", y, x);
break;
}
this.AddDataRow(solution, string.Format("{0}.", row), token.Element, string.Empty, (!hasError) ? (variables.Count > 0) ? string.Format("{0}, {1}", this.PrintStack(variables), calc) : calc : message);
variables.Push(result);
}
else
{
variables.Push(token.Value);
this.AddDataRow(solution, string.Format("{0}.", row), token.Element, token.Value.ToString(), (hasError) ? message : this.PrintStack(variables));
}
}
double answer = 0.0;
if (variables.Count > 0)
{
answer = variables.Pop();
this.AddDataRow(solution, string.Format("{0}.", row + 1), string.Empty, string.Empty, (!hasError) ? answer.ToString() : message);
}
return answer;
}
protected virtual string PrintStack(Stack<double> stack)
{
return (stack.Count > 0) ? stack.ToList().Select(s => s.ToString()).Reverse().Aggregate((current, next) => current + ", " + next) : string.Empty;
}
private void AddDataRow(DataTable dt, string index, string postfix, string value, string answer)
{
DataRow dr = dt.NewRow();
dr.SetField<string>("Index", index);
dr.SetField<string>("Postfix", postfix);
dr.SetField<string>("Value", value);
dr.SetField<string>("Answer", answer);
dt.Rows.Add(dr);
}
}
}
Date :
2016-02-10 09:08:20
By :
ห้ามตอบเกินวันละ 2 กระทู้
No. 14
Guest
PrefixNotation.cs
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace InfixNotationConverter
{
public class PrefixNotation : PostfixNotation
{
public override bool IsSuccess(out string message)
{
Stack<Token> prefix = this.ToStack();
Stack<double> variables = new Stack<double>();
bool isSuccess = true;
message = "Success";
while (prefix.Count > 0)
{
Token token = prefix.Pop();
string calc = string.Empty;
if (token.Type == ElementType.Operator)
{
double x = 0.0;
double y = 0.0;
double result = 0.0;
if (variables.Count > 0)
{
x = variables.Pop();
if (variables.Count > 0)
{
y = variables.Pop();
}
else
{
isSuccess = false;
message = "Error: Syntax error.";
}
}
else
{
isSuccess = false;
message = "Error: Syntax error.";
}
switch (token.Element)
{
case "^": result = Math.Pow(x, y); break;
case "*": result = x * y; break;
case "/":
if (y != 0)
{
result = x / y;
}
else
{
isSuccess = false;
message = "Error: Devide by zero.";
}
break;
case "+": result = x + y; break;
case "-": result = x - y; break;
}
variables.Push(result);
}
else
{
variables.Push(token.Value);
}
}
return isSuccess;
}
public override double Calculate(out DataTable solution)
{
Stack<Token> prefix = this.ToStack();
Stack<double> variables = new Stack<double>();
bool hasError = false;
string message = string.Empty;
int row = 0;
solution = new DataTable();
solution.Columns.Add(new DataColumn("Index", typeof(string)));
solution.Columns.Add(new DataColumn("Prefix", typeof(string)));
solution.Columns.Add(new DataColumn("Value", typeof(string)));
solution.Columns.Add(new DataColumn("Answer", typeof(string)));
while (prefix.Count > 0)
{
Token token = prefix.Pop();
row++;
if (token.Type == ElementType.Operator)
{
string calc = string.Empty;
double x = 0.0;
double y = 0.0;
double result = 0.0;
if (variables.Count > 0)
{
x = variables.Pop();
if (variables.Count > 0)
{
y = variables.Pop();
}
else
{
hasError = true;
message = "Error: Syntax error.";
}
}
else
{
hasError = true;
message = "Error: Syntax error.";
}
switch (token.Element)
{
case "^":
result = Math.Pow(x, y);
calc = (hasError) ? string.Empty : string.Format("{0}^{1}", x, y);
break;
case "*":
result = x * y;
calc = (hasError) ? string.Empty : string.Format("{0}*{1}", x, y);
break;
case "/":
if (y != 0)
{
result = x / y;
calc = (hasError) ? string.Empty : string.Format("{0}/{1}", x, y);
}
else
{
hasError = true;
message = "Error: Devide by zero.";
}
break;
case "+":
result = x + y;
calc = (hasError) ? string.Empty : string.Format("{0}+{1}", x, y);
break;
case "-":
result = x - y;
calc = (hasError) ? string.Empty : string.Format("{0}-{1}", x, y);
break;
}
this.AddDataRow(solution, string.Format("{0}.", row), token.Element, string.Empty, (!hasError) ? (variables.Count > 0) ? string.Format("{0}, {1}", calc, this.PrintStack(variables)) : calc : message);
variables.Push(result);
}
else
{
variables.Push(token.Value);
this.AddDataRow(solution, string.Format("{0}.", row), token.Element, token.Value.ToString(), (hasError) ? message : this.PrintStack(variables));
}
}
double answer = 0.0;
if (variables.Count > 0)
{
answer = variables.Pop();
this.AddDataRow(solution, string.Format("{0}.", row + 1), string.Empty, string.Empty, (!hasError) ? answer.ToString() : message);
}
return answer;
}
protected override string PrintStack(Stack<double> stack)
{
return (stack.Count > 0) ? stack.ToList().Select(s => s.ToString()).Reverse().Aggregate((current, next) => next + ", " + current) : string.Empty;
}
private void AddDataRow(DataTable dt, string index, string prefix, string value, string answer)
{
DataRow dr = dt.NewRow();
dr.SetField<string>("Index", index);
dr.SetField<string>("Prefix", prefix);
dr.SetField<string>("Value", value);
dr.SetField<string>("Answer", answer);
dt.Rows.Add(dr);
}
}
}