用 C# 编程实现读写Binary
五一时去朋友那, 他问了个小问题, 只要写几十行代码就可以很好的说明问题.可偏偏机子没装VS, 只好做罢.回来后想想, 要是有个在线的C#IDE就好了.于是上网查了下相关的资料, 整出来个简单的在线C#IDE.
0 N% C2 ~8 y0 G( d) p3 a% T; M8 R3 d1 v; b% Y; o8 G& }
做这个,主要要解决两个问题, 一是如果将网页上文本框的代码编译并执行;二是如果将程序运行结果在网页上输出., ~3 Y# D& w5 C! Z* g% O, A, I
. f7 {3 T% \. y: u/ z* Z
第一个问题不难, .NET已经有现成的C#编译类CSharpCodeProvider(或是其它语言的),再使用CompilerParameters类做为编译参数,就可以很容易的实现.打造最好的电脑自学交流论坛6 C* ]# l- H& z5 P( G
. [, `, D% C9 I; {$ w: F 第二个问题, 举最简单情况, 就是将Console.Write方法输出的内容在网页上显示出来.这其实也很好办,只要在编译之前, 在输出语句做一个替换, 将输出的内容存到另一个地方.等运行结束后, 再从那个地方取出来就是了.7 E% f) K9 n0 _# l* ?% ?
我爱电脑技术论坛# D) Y# x8 U( V2 m! D2 P9 e8 U ~
代码实现如下: 我爱电脑技术论坛/ n3 a1 o) T; u. A
, z" `) E" T r4 b" g
以下是引用片段:
" k0 ?) ]# N# J8 ]" @- `, r using System; 5 V8 r5 Q7 p( n6 D6 H
using System.Collections.Generic; www.520diannao.com d5 \8 @; ?4 C7 T% Q% n% f$ k
using System.Linq;
) m1 M* f( V' v( Iwww.520diannao.com using System.Text;
0 |0 g* a6 [* s; u6 }# ^ www.520diannao.com0 H) l4 c3 P# A' `1 k
namespace VSOnline.Framework
7 S' g1 y6 E1 ?& f/ |$ d/ ?5 r+ I9 z( \ {
" Q8 C) ]- n' W) y, x% r, o' @ /**////
! t+ B7 v- y7 u0 }1 P3 X /// 自定义的输出类
- h8 \& g& m" F; ^( j* Y7 ?# [我爱电脑技术论坛 /// & A$ v; O+ w" H" R9 j
public class Consoler
7 X; O" q1 f$ q { ' @. U6 ~8 J: ?2 d! s$ K
//存储所有输出 我爱电脑技术论坛( k* N/ s& Y; X
public static Dictionary Outputs { get; set; }
# U( N O8 o4 F( g- y' p8 ` ( u* }0 y' @ c) J2 x7 g
static Consoler()
7 M7 j+ ~/ F6 y' I2 Z" g我爱电脑技术论坛 { 我爱电脑技术论坛' k! R9 ?& q- p8 g, `
Outputs = new Dictionary(); : S( [7 t ?, E6 L. d. e) [' \
} - c+ ?9 l7 N! w" T
4 {, A6 `$ G( N1 E E2 k
输出操作#region 输出操作 我爱电脑技术论坛# [1 \ {- `; y2 t- i3 c5 `; R' h2 {& e
. A6 Q7 B0 } k3 F) D我爱电脑技术论坛 //当前输出 / W3 q# B5 s9 _: \ r0 r
public List Output { get; private set; } 我爱电脑技术论坛; R4 J: i# W, g4 D- n
打造最好的电脑自学交流论坛% ]0 b: x9 ^. ^, z# d3 Y" a2 x
public Consoler() 打造最好的电脑自学交流论坛# J' h2 h# ?0 ?3 Q0 i6 E ~# j
{ www.520diannao.com& n( H' O5 s* b0 @: h
Output = new List();
% G, q1 U' C9 J( K3 j; o& ?www.520diannao.com }
( |1 Q& g* F; F, j. a8 u0 h我爱电脑技术论坛
3 o+ G/ B- t& C4 g6 M public void Write(object str) % Y3 U: p2 [8 {% G; l
{
' K. A8 b! y- g打造最好的电脑自学交流论坛 Output.Add(str.ToString());
6 K4 x1 ?2 E* J3 z9 Jwww.520diannao.com }
: Z$ K- m) w! ]% A2 \) ?% j我爱电脑技术论坛 打造最好的电脑自学交流论坛/ {+ P6 o/ S8 V# m2 b# T1 U
public void WriteLine(object str)
0 s/ T9 O! e' a3 V {
# Z) v! Q, t- l Q0 r* z我爱电脑技术论坛 Output.Add(str.ToString() + ""); 2 \" i3 J6 E6 i7 j
}
- d. N1 C. N nwww.520diannao.com
1 R& y2 t7 r- Q& z$ E8 h8 M6 vwww.520diannao.com #endregion
4 O% a9 s1 m) Y. L1 xwww.520diannao.com }
# u8 Y( T2 P8 x- I+ ]' jwww.520diannao.com }
5 k7 W) B4 V7 j) T1 _: d( ~ |0 wwww.520diannao.com using System; 打造最好的电脑自学交流论坛9 h4 n. g. t: r5 C
using System.Reflection;
1 S4 C# M! F6 E/ j6 i" R1 E) ]0 J+ n我爱电脑技术论坛 using Microsoft.CSharp; www.520diannao.com7 d( C" a+ t6 V- p) W
using System.CodeDom.Compiler;
) p# z$ o# Y+ Y# H9 ^- P" Bwww.520diannao.com using System.Collections.Generic;
6 [2 f+ p& {; U6 h5 \; b打造最好的电脑自学交流论坛 using System.Linq;
8 k7 l; j' {5 W% Y* H using System.Web; www.520diannao.com" s& b( W4 m) k' z6 [! Y- `( e( ?5 x/ l
: n9 r& G$ H# j- f% Z" g4 b namespace VSOnline.Framework , M/ F6 c1 ^0 A) P4 o/ M
{
. |+ k" t; h7 G0 ?/ U$ P /**////
% b) r4 [9 y# S4 M U3 xwww.520diannao.com /// 代码执行类
2 J* t. `- x* z3 T1 i ///
; z& n$ k+ B$ B3 ]9 |+ w public class CodeRun
7 M h% n0 H( }; E; k( [ { + v0 S0 \8 ?' [& ^& [9 d
/**////
7 \0 {8 Z" @5 t* y9 \, m /// Framework版本,可选择v2.0, v3.0, v3.5
7 B6 O- J, H: G- @7 q* G% Q- x( Z我爱电脑技术论坛 /// . J6 i- x& m, M( G+ ~
private string CompilerVersion { get; set; } ) J) ~: ?/ r) R4 }- f( l
5 [: H$ [ x K& @# k7 y( f /**//// ' N4 D: u$ {* o. }) d
/// 构造函数 我爱电脑技术论坛$ l( Z3 B( x' U R* ^0 D( X
///
! k. v, O- f* e) I% q0 f g. ?打造最好的电脑自学交流论坛 /// Framework版本,可选择v2.0, v3.0, v3.5 我爱电脑技术论坛5 d4 q, Y# N6 L: ]" R
public CodeRun(string compilerVersion)
, f# g G# _: B; owww.520diannao.com {
9 b' p3 b" W r4 M+ ?) Y! m: A打造最好的电脑自学交流论坛 CompilerVersion = compilerVersion; & `, X. _7 Q: T3 d: N' ~- Z' b( o
} www.520diannao.com( ? x9 c8 K! ^4 N7 N R0 b
1 K( k+ ?+ q8 B* L+ ~4 R; k' q' E
/**////
. N" n5 h& s7 @% [ /// 构造函数,默认为3.5版本
+ }' [& D# k5 D$ w2 X% X ///
# S) s6 X" P: O) @打造最好的电脑自学交流论坛 public CodeRun() 打造最好的电脑自学交流论坛9 }: R2 S3 b; I f! O
{ ! o7 M5 c/ g9 a: t; U
CompilerVersion = "v3.5"; 2 A% [3 w! i9 r2 v
} , m+ D6 t: L. v7 d) a
0 u4 m( C, I) K% }打造最好的电脑自学交流论坛 /**////
$ e% G- |8 I- V4 I打造最好的电脑自学交流论坛 /// 动态编译并执行代码
9 w$ C# u$ X1 } z7 p- o /// www.520diannao.com2 J7 @! `( r2 }- y) g% K/ u9 p# y
/// 代码 3 W. Y9 t3 `; W" u; y- k
/// 返回输出内容
# e: ]5 m8 n Xwww.520diannao.com public List Run(string code, string id, params string[] assemblies)
9 K% t& L8 W" S$ h打造最好的电脑自学交流论坛 { 我爱电脑技术论坛4 B1 m+ E) m; S, n4 r) a' Y& U9 R
Consoler.Outputs.Add(id, new Consoler()); www.520diannao.com6 g6 ?! ~4 o5 Y. Y f
CompilerParameters compilerParams = new CompilerParameters();
! h0 f3 J" ?4 |7 N( V+ [! Z打造最好的电脑自学交流论坛 //编译器选项设置
# g: a( t. @9 q compilerParams.CompilerOptions = "/target:library /optimize"; * w, z, ?5 B0 t, z( D
//compilerParams.CompilerOptions += @" /lib:""C:\Program Files\Reference Assemblies\Microsoft\Framework\v3.5\""";
2 X' Y7 q7 t5 e9 e$ Q打造最好的电脑自学交流论坛 //编译时在内存输出 www.520diannao.com" k9 g5 ^# n- p+ t
compilerParams.GenerateInMemory = true; 打造最好的电脑自学交流论坛& a: g. j9 K5 r/ F2 t7 w& q* C% ~
//生成调试信息
; |6 s$ d- P: Y compilerParams.IncludeDebugInformation = false; & ^- ^4 f, {# w2 _4 [6 n4 R
//添加相关的引用 我爱电脑技术论坛, ]5 Y2 D: G7 G5 W' I; |
foreach (string assembly in assemblies) * ~# h% p4 T5 t! a: ?1 K
{
3 S- I! ?6 u8 L: p' `1 ?/ N) T compilerParams.ReferencedAssemblies.Add(assembly); 6 `! L% ]2 |1 |( p5 S/ }: O
} , z* C0 f' l! F. ~" `9 P
compilerParams.ReferencedAssemblies.Add("mscorlib.dll");
8 J( l' l: N0 Q" k! wwww.520diannao.com compilerParams.ReferencedAssemblies.Add("System.dll"); 0 ^' Y8 r! B4 L1 t1 v
if (this.CompilerVersion == "v3.5") 打造最好的电脑自学交流论坛, |( t( U' O& `+ f( T" c6 ^
{ - }' r: A& |* e: y! W- D* _* ], f
compilerParams.ReferencedAssemblies.Add("System.Core.dll");
2 y; p+ D; Z) X( X我爱电脑技术论坛 }
) I4 E! f& B! Z % l' K; _. K8 D* L, K$ e
string path = "";
, m/ [: E& m' F" q5 V" n! ?打造最好的电脑自学交流论坛 try
7 X9 ?% \: d, X2 }; w( ^# U- ~0 L {
! ~+ @/ `. f# ]/ ~我爱电脑技术论坛 path = HttpContext.Current.Server.MapPath("/bin/");
4 ~$ p+ A1 H7 n# ]" i. ^, n# c! a } ) J$ G8 x& f( b. e& i9 [
catch { }
& f$ ]7 b; T! c
. s7 w' `3 J2 a- U& R compilerParams.ReferencedAssemblies.Add(path + "VSOnline.Framework.dll");
# A) o) ^# Q. t CSharpCodeProvider compiler = new CSharpCodeProvider(new Dictionary() { { "CompilerVersion", CompilerVersion } }); www.520diannao.com" v9 C1 m5 w* D. J0 a; K# f
//编译
* b/ I% P0 L: ]) ~www.520diannao.com code = code.Replace("Console.WriteLine", string.Format("VSOnline.Framework.Consoler.Outputs[\"{0}\"].WriteLine", id)); 4 Z: W* e! B' M2 ?. d6 F
code = code.Replace("Console.Write", string.Format("VSOnline.Framework.Consoler.Outputs[\"{0}\"].Write", id)); , R U: [6 e, j: }* F1 t3 X: h$ }0 S
CompilerResults results = compiler.CompileAssemblyFromSource(compilerParams, code);
# n% `# j% h# _7 n) ^/ @ //错误
+ }5 z8 D/ c" o ]/ v打造最好的电脑自学交流论坛 if (results.Errors.HasErrors)
" u" l" H; W8 X g% \3 d我爱电脑技术论坛 {
( Z7 }7 N/ E0 y) ^2 ]& @我爱电脑技术论坛 foreach (CompilerError error in results.Errors)
3 H$ |6 I0 P0 ^ { 我爱电脑技术论坛' o2 f& ]! S7 t
Consoler.Outputs[id].Output.Add(error.ErrorText + ""); 我爱电脑技术论坛+ t8 ~3 Z3 o1 s9 f- D- y1 Z: l6 a+ q/ \
} ! q. l( @& {8 d8 ~: Q3 C
$ E1 @, |/ N' Zwww.520diannao.com return ReturnOutput(id); 1 q. i# }/ x# c: \+ V9 E) h
} www.520diannao.com& R+ y5 `% r1 _. ]% u3 ^$ J
//创建程序集 www.520diannao.com% p) C' H! e* }! }3 c
Assembly asm = results.CompiledAssembly; 我爱电脑技术论坛: D- n. z& K* j
//获取编译后的类型 www.520diannao.com, g1 k1 O: X, Y s2 u; x8 D
object mainClass = asm.CreateInstance("Program");
: K! A1 E3 h! Q7 O# o, z9 I Type mainClassType = mainClass.GetType(); $ @0 Z( H/ H& I% W# K) `
//输出结果
) f' F0 {6 O3 Q5 V( K mainClassType.GetMethod("Main").Invoke(mainClass, null); www.520diannao.com8 }; y& B W- z4 p( u& R0 p# `
m/ `- k' x; k( A$ G- m& s8 [ c3 _2 E# r return ReturnOutput(id);
& \# `' [( j2 @, t打造最好的电脑自学交流论坛 }
# L2 N j( U% [8 C' P) q
, t$ D+ |) K- @/ ? Z* Twww.520diannao.com private List ReturnOutput(string id) & s6 G4 f( m) R7 ^! w; D) x- z [
{
1 ?6 ^" x1 f9 Z0 C. O打造最好的电脑自学交流论坛 string[] output = new string[Consoler.Outputs[id].Output.Count]; $ ?& C) Z. b" Y Y4 u0 y
Consoler.Outputs[id].Output.CopyTo(output, 0);
; [) j1 T0 ^" Z9 K/ wwww.520diannao.com Consoler.Outputs.Remove(id); + y7 l# p3 a ` ]( D% c
www.520diannao.com! M. i$ F4 e6 s& j
return output.ToList();
# j/ Z# S5 I9 H+ X } 8 T5 Y% l8 c) q/ o5 Q$ y. t \% D
} |# F5 F. c; z9 W# Y ~
}