Parser stuff
This commit is contained in:
		
							parent
							
								
									7acaa9df76
								
							
						
					
					
						commit
						abbd4a74ef
					
				
					 25 changed files with 1044 additions and 32 deletions
				
			
		
							
								
								
									
										91
									
								
								ShintenScriptTest/EvaluationTest.cs
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										91
									
								
								ShintenScriptTest/EvaluationTest.cs
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,91 @@ | |||
| using Microsoft.VisualStudio.TestTools.UnitTesting; | ||||
| using ShintenScript; | ||||
| using System; | ||||
| using System.Collections.Generic; | ||||
| using System.Linq; | ||||
| using System.Text; | ||||
| using System.Threading.Tasks; | ||||
| 
 | ||||
| namespace ShintenScriptTest | ||||
| { | ||||
|     [TestClass] | ||||
|     public class EvaluationTest | ||||
|     { | ||||
|         [TestMethod] | ||||
|         public void TestBlock() | ||||
|         { | ||||
|             IASTNode ast = new ASTNodeBlock(new List<IASTNode>() | ||||
|             { | ||||
|                 new ASTNodeLiteral(1f), | ||||
|                 new ASTNodeLiteral(true), | ||||
|                 new ASTNodeLiteral(5f) | ||||
|             }); | ||||
| 
 | ||||
|             Assert.AreEqual(SSType.real, ast.Type()); | ||||
| 
 | ||||
|             Func<ExecutionContext, float> func = (Func<ExecutionContext, float>)ast.CreateFunction(); | ||||
| 
 | ||||
|             Assert.AreEqual(5f, func(null)); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestAdd() | ||||
|         { | ||||
|             IASTNode ast = new ASTNodeAdd(new ASTNodeLiteral(2f), new ASTNodeLiteral(3f)); | ||||
| 
 | ||||
|             Assert.AreEqual(SSType.real, ast.Type()); | ||||
| 
 | ||||
|             Func<ExecutionContext, float> func = (Func<ExecutionContext, float>)ast.CreateFunction(); | ||||
| 
 | ||||
|             Assert.AreEqual(5f, func(null)); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestMul() | ||||
|         { | ||||
|             IASTNode ast = new ASTNodeMultiply(new ASTNodeLiteral(2f), new ASTNodeLiteral(3f)); | ||||
| 
 | ||||
|             Assert.AreEqual(SSType.real, ast.Type()); | ||||
| 
 | ||||
|             Func<ExecutionContext, float> func = (Func<ExecutionContext, float>)ast.CreateFunction(); | ||||
| 
 | ||||
|             Assert.AreEqual(6f, func(null)); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestSub() | ||||
|         { | ||||
|             IASTNode ast = new ASTNodeSubtract(new ASTNodeLiteral(2f), new ASTNodeLiteral(3f)); | ||||
| 
 | ||||
|             Assert.AreEqual(SSType.real, ast.Type()); | ||||
| 
 | ||||
|             Func<ExecutionContext, float> func = (Func<ExecutionContext, float>)ast.CreateFunction(); | ||||
| 
 | ||||
|             Assert.AreEqual(-1f, func(null)); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestDiv() | ||||
|         { | ||||
|             IASTNode ast = new ASTNodeDivide(new ASTNodeLiteral(7f), new ASTNodeLiteral(2f)); | ||||
| 
 | ||||
|             Assert.AreEqual(SSType.real, ast.Type()); | ||||
| 
 | ||||
|             Func<ExecutionContext, float> func = (Func<ExecutionContext, float>)ast.CreateFunction(); | ||||
| 
 | ||||
|             Assert.AreEqual(3.5f, func(null)); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestNegative() | ||||
|         { | ||||
|             IASTNode ast = new ASTNodeNegative(new ASTNodeLiteral(7f)); | ||||
| 
 | ||||
|             Assert.AreEqual(SSType.real, ast.Type()); | ||||
| 
 | ||||
|             Func<ExecutionContext, float> func = (Func<ExecutionContext, float>)ast.CreateFunction(); | ||||
| 
 | ||||
|             Assert.AreEqual(-7f, func(null)); | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  | @ -19,6 +19,7 @@ namespace ShintenScriptTest | |||
|                 1.5e6 | ||||
|                 2.4e-6 | ||||
| 
 | ||||
|                 ; | ||||
|                 ( ) { } | ||||
|                 + - * / | ||||
|                 > < == >= <= != | ||||
|  | @ -36,6 +37,7 @@ namespace ShintenScriptTest | |||
|                 new Token { type = Token.Type.NUMBER, data = 1.5e6f }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2.4e-6f }, | ||||
| 
 | ||||
|                 new Token { type = Token.Type.SEMICOLON }, | ||||
|                 new Token { type = Token.Type.LPAREN }, | ||||
|                 new Token { type = Token.Type.RPAREN }, | ||||
|                 new Token { type = Token.Type.LBRACE }, | ||||
|  | @ -59,8 +61,18 @@ namespace ShintenScriptTest | |||
|                 new Token { type = Token.Type.IF }, | ||||
|                 new Token { type = Token.Type.WHILE }, | ||||
|                 new Token { type = Token.Type.FN }, | ||||
|             })); | ||||
|         } | ||||
| 
 | ||||
|                 new Token { type = Token.Type.EOF }, | ||||
|         [TestMethod] | ||||
|         public void TestHexExponent() | ||||
|         { | ||||
|             Lexer lexer = new Lexer(@"0xcafe-1337"); | ||||
| 
 | ||||
|             Assert.IsTrue(lexer.TokenStream().SequenceEqual(new Token[] { | ||||
|                 new Token { type = Token.Type.NUMBER, data = 51966f }, | ||||
|                 new Token { type = Token.Type.MINUS }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 1337f }, | ||||
|             })); | ||||
|         } | ||||
|     } | ||||
|  |  | |||
							
								
								
									
										153
									
								
								ShintenScriptTest/ParserTest.cs
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										153
									
								
								ShintenScriptTest/ParserTest.cs
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,153 @@ | |||
| using Microsoft.VisualStudio.TestTools.UnitTesting; | ||||
| using ShintenScript; | ||||
| using System; | ||||
| using System.Collections.Generic; | ||||
| using System.Linq; | ||||
| using System.Text; | ||||
| using System.Threading.Tasks; | ||||
| 
 | ||||
| namespace ShintenScriptTest | ||||
| { | ||||
|     [TestClass] | ||||
|     public class ParserTest | ||||
|     { | ||||
|         [TestMethod] | ||||
|         public void TestBlock() | ||||
|         { | ||||
|             Lexer lexer = new ScaffoldLexer(new Token[] | ||||
|             { | ||||
|                 new Token { type = Token.Type.LBRACE }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 1f }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2f }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 3f }, | ||||
|                 new Token { type = Token.Type.RBRACE }, | ||||
|             }); | ||||
| 
 | ||||
|             IASTNode ast = new Parser(lexer).ParseExpression(); | ||||
| 
 | ||||
|             if (ast is ASTNodeBlock block) | ||||
|             { | ||||
|                 Assert.AreEqual(3, block.statements.Count); | ||||
|                 Assert.IsInstanceOfType(block.statements[0], typeof(ASTNodeLiteral)); | ||||
|                 Assert.IsInstanceOfType(block.statements[1], typeof(ASTNodeLiteral)); | ||||
|                 Assert.IsInstanceOfType(block.statements[2], typeof(ASTNodeLiteral)); | ||||
|             } | ||||
|             else Assert.Fail(); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestComparison() | ||||
|         { | ||||
|             Lexer lexer = new ScaffoldLexer(new Token[] | ||||
|             { | ||||
|                 new Token { type = Token.Type.NUMBER, data = 1f }, | ||||
|                 new Token { type = Token.Type.LE }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2f }, | ||||
|                 new Token { type = Token.Type.NE }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 3f }, | ||||
|             }); | ||||
| 
 | ||||
|             IASTNode ast = new Parser(lexer).ParseExpression(); | ||||
| 
 | ||||
|             if (ast is ASTNodeComparison comp) | ||||
|             { | ||||
|                 Assert.AreEqual(3, comp.nodes.Count); | ||||
|                 Assert.AreEqual(2, comp.comparisons.Count); | ||||
|                 Assert.IsInstanceOfType(comp.nodes[0], typeof(ASTNodeLiteral)); | ||||
|                 Assert.IsInstanceOfType(comp.nodes[1], typeof(ASTNodeLiteral)); | ||||
|                 Assert.IsInstanceOfType(comp.nodes[2], typeof(ASTNodeLiteral)); | ||||
|                 Assert.AreEqual(Token.Type.LE, comp.comparisons[0]); | ||||
|                 Assert.AreEqual(Token.Type.NE, comp.comparisons[1]); | ||||
|             } | ||||
|             else Assert.Fail(); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestDivision() | ||||
|         { | ||||
|             Lexer lexer = new ScaffoldLexer(new Token[] | ||||
|             { | ||||
|                 new Token { type = Token.Type.NUMBER, data = 1f }, | ||||
|                 new Token { type = Token.Type.SLASH }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2f }, | ||||
|             }); | ||||
| 
 | ||||
|             IASTNode ast = new Parser(lexer).ParseExpression(); | ||||
| 
 | ||||
|             Assert.IsInstanceOfType(ast, typeof(ASTNodeDivide)); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestMinus() | ||||
|         { | ||||
|             Lexer lexer = new ScaffoldLexer(new Token[] | ||||
|             { | ||||
|                 new Token { type = Token.Type.MINUS }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2f }, | ||||
|                 new Token { type = Token.Type.MINUS }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 3f }, | ||||
|             }); | ||||
| 
 | ||||
|             IASTNode ast = new Parser(lexer).ParseExpression(); | ||||
| 
 | ||||
|             if (ast is ASTNodeSubtract sub) | ||||
|             { | ||||
|                 Assert.IsInstanceOfType(sub.lhs, typeof(ASTNodeNegative)); | ||||
|                 Assert.IsInstanceOfType(sub.rhs, typeof(ASTNodeLiteral)); | ||||
|             } | ||||
|             else Assert.Fail(); | ||||
|         } | ||||
| 
 | ||||
|         [TestMethod] | ||||
|         public void TestOrderOfOperations() | ||||
|         { | ||||
|             Lexer lexer = new ScaffoldLexer(new Token[] | ||||
|             { | ||||
|                 new Token { type = Token.Type.NUMBER, data = 1f }, | ||||
|                 new Token { type = Token.Type.PLUS }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2f }, | ||||
|                 new Token { type = Token.Type.ASTERISK }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 3f }, | ||||
|             }); | ||||
| 
 | ||||
|             IASTNode ast = new Parser(lexer).ParseExpression(); | ||||
| 
 | ||||
|             if (ast is ASTNodeAdd add) | ||||
|             { | ||||
|                 Assert.IsInstanceOfType(add.lhs, typeof(ASTNodeLiteral)); | ||||
| 
 | ||||
|                 if (add.rhs is ASTNodeMultiply mul) | ||||
|                 { | ||||
|                     Assert.IsInstanceOfType(mul.lhs, typeof(ASTNodeLiteral)); | ||||
|                     Assert.IsInstanceOfType(mul.rhs, typeof(ASTNodeLiteral)); | ||||
|                 } | ||||
|                 else Assert.Fail(); | ||||
|             } | ||||
|             else Assert.Fail(); | ||||
| 
 | ||||
|             lexer = new ScaffoldLexer(new Token[] | ||||
|             { | ||||
|                 new Token { type = Token.Type.NUMBER, data = 1f }, | ||||
|                 new Token { type = Token.Type.ASTERISK }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 2f }, | ||||
|                 new Token { type = Token.Type.PLUS }, | ||||
|                 new Token { type = Token.Type.NUMBER, data = 3f }, | ||||
|             }); | ||||
| 
 | ||||
|             ast = new Parser(lexer).ParseExpression(); | ||||
| 
 | ||||
|             if (ast is ASTNodeAdd add2) | ||||
|             { | ||||
|                 Assert.IsInstanceOfType(add2.rhs, typeof(ASTNodeLiteral)); | ||||
| 
 | ||||
|                 if (add2.lhs is ASTNodeMultiply mul) | ||||
|                 { | ||||
|                     Assert.IsInstanceOfType(mul.lhs, typeof(ASTNodeLiteral)); | ||||
|                     Assert.IsInstanceOfType(mul.rhs, typeof(ASTNodeLiteral)); | ||||
|                 } | ||||
|                 else Assert.Fail(); | ||||
|             } | ||||
|             else Assert.Fail(); | ||||
|         } | ||||
|     } | ||||
| } | ||||
							
								
								
									
										27
									
								
								ShintenScriptTest/ScaffoldLexer.cs
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										27
									
								
								ShintenScriptTest/ScaffoldLexer.cs
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,27 @@ | |||
| using ShintenScript; | ||||
| using System; | ||||
| using System.Collections.Generic; | ||||
| using System.Linq; | ||||
| using System.Text; | ||||
| using System.Threading.Tasks; | ||||
| 
 | ||||
| namespace ShintenScriptTest | ||||
| { | ||||
|     class ScaffoldLexer : Lexer | ||||
|     { | ||||
|         Queue<Token> tokenQueue; | ||||
| 
 | ||||
|         public ScaffoldLexer(IEnumerable<Token> queue) : base("") | ||||
|         { | ||||
|             tokenQueue = new Queue<Token>(queue); | ||||
|         } | ||||
| 
 | ||||
|         public override Token ParseOne() | ||||
|         { | ||||
|             if (tokenQueue.Count == 0) | ||||
|                 return new Token { type = Token.Type.EOF }; | ||||
| 
 | ||||
|             return tokenQueue.Dequeue(); | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  | @ -49,8 +49,11 @@ | |||
|     <Reference Include="System.Core" /> | ||||
|   </ItemGroup> | ||||
|   <ItemGroup> | ||||
|     <Compile Include="EvaluationTest.cs" /> | ||||
|     <Compile Include="LexerTests.cs" /> | ||||
|     <Compile Include="ParserTest.cs" /> | ||||
|     <Compile Include="Properties\AssemblyInfo.cs" /> | ||||
|     <Compile Include="ScaffoldLexer.cs" /> | ||||
|   </ItemGroup> | ||||
|   <ItemGroup> | ||||
|     <None Include="packages.config" /> | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Sen
						Sen