02 2012 档案
.NET(C#):设置文件系统对象的访问控制
摘要: 我之前写过几篇关于Windows访问控制的文章: 浅谈Windows访问控制在.NET(C#)中的实现(ACE, SD, DACL, SACL) .NET(C#):使用访问控制创建一个只有当前用户可以访问的文件 .NET(C#):使用ObjectSecurity.SetAccessRuleProtection保留访问控制数据 这篇文章起到一定的补充作用。 讲一下在Windows下(具体是在Windows 7下)设置一个文件系统对象访问控制,比如我们想让这个对象只能被拥有者访问(和控制),同时这个对象不继承任何父容器的控制选项。 那么属性的安全... 阅读全文
WPF 3D:使用GeometryModel3D的BackMaterial
摘要: 使用BackMaterial,我们可以定义3D物体的内部材质(或者说是背面),比如,我们定义一个四方体容器,外面现实的是普通材质,里面的则是内部材质。比如下图,红色的是内部材质: GeometryModel3D.BackMaterial默认是null,所以如果不定义他的话,背面的材质是不会显示,上面的程序则会运行成这样: 定义材质很简单,设置GeometryModel3D.Material属性和BackMaterial,放置任何一个继承与Material类型的对象,这里就以最普通的DiffuseMaterial做示范: <GeometryModel3D.Mate... 阅读全文
WPF 3D:MeshGeometry3D的定义和光照
摘要: 由于WPF计算光照会根据整个平面的方向向量,所以如果在不同面上使用同一个点可能会达到不同的光照效果。让我们用不同的定义Mesh的方法来演示这个问题。 首先要定义两个简单的相交面,为方便定义,整个图形的主视图可以参考下图: 第一个方法就是用最简单的最笨的方法,一次性定义所有的点,这样两个面四个三角形一共12个点,TriangleIndices是从0到11. 如下代码: <MeshGeometry3D Positions="-1 0 0, 0 0 1, 0 1 1, -1 0 0, 0 1 1, -1 1 0, 0 0 1, 1 0 0, 1 1 0, 0 0 ... 阅读全文
.NET(C#):线程本地存储(Thread-Local Storage)之ThreadStatic, LocalDataStoreSlot和ThreadLocal<T>
摘要: 目录 1. 使用ThreadStatic特性 2. 使用命名的LocalDataStoreSlot类型 3. 使用未命名的LocalDataStoreSlot类型 4. 使用.NET 4.0的ThreadLocal<T>类型 5. 强调一下不同方法和TLS的默认值 注:为了简洁,下面将以”TLS”三个字母代替”线程本地存储(Thread-Local Storage)”。 返回目录 1. 使用ThreadStatic特性 ThreadStatic特性是最简单的TLS使用,且只支持静... 阅读全文
WPF 3D: MeshGeometry3D纹理坐标的正确定义
摘要: 为了使基于2D的纹理显示在3D对象中,我们必须定义3D Mesh对象的纹理贴图坐标。在WPF中,此项功能则通过MeshGeometry3D.TextureCoordinates属性。 2D纹理的对应坐标和WPF的LinearGradientBrush的StartPoint和EndPoint一样。 下图来自MSDN关于LinearGradientBrush的StartPoint的说明: ... 阅读全文
.NET(C#):ConcurrentBag<T>同线程元素的添加和删除
摘要: ConcurrentBag<T>对于同一个线程值的添加和删除是非常快的,因为ConcurrentBag内部将数据按线程的标识而独立存储,所以一个线程从自己的数据中移除一个数据是非常快的,当然如果这个线程中没有数据,那么只能从其他线程中移除数据,此时会发生一些性能损耗从而确保线程安全! 比如从线程1中加入两个数据,在线程2中加入一个数据。那么当线程2调用TryTake时,被移除的数据肯定是线程2加入的那个数据: //+ using System.Threading.Tasks; //+ using System.Collections.Concurrent; ... 阅读全文
.NET(C#) TPL:Task中未觉察异常和TaskScheduler.UnobservedTaskException事件
摘要: 当你在一个Task执行中抛出异常,比如: Task.Factory.StartNew(() => { throw new Exception(); }); 运行该方法,没有任何异常抛出。 事实上此时Task的异常处于未觉察状态,这个未觉察状态的异常会在垃圾回收时终结器执行线程中被抛出。 为了诱发这个异常,我们可以通过GC.Collect来强制垃圾回收从而引发终结器处理线程,此时Task的未觉察异常会被抛出。 //在Task中抛出异常 Task.Factory.StartNew(() => { throw new ... 阅读全文
.NET(C#) TPL:Task, Parallel, PLINQ中取消操作后的OperationCanceledException异常
摘要: 对于Task,取消后的OperationCanceledException异常会成为TaskCanceledException并且会被包装在AggregateException中。 var src = new CancellationTokenSource(); var task = Task.Factory.StartNew(() => { Thread.Sleep(500); src.Token.ThrowIfCancellationRequested(); }, src.Token); src.Cancel(); ... 阅读全文
.NET(C#) TPL:Parallel循环和多个Task的异常处理
摘要: 和for/foreach中发生异常的表现一样,Parallel循环中的任何异常都会使整个循环终止,注意由于整个循环是分块同时进行的,因此整个循环不会立即终止(如果有一个线程正在进行长时间工作的话,而且是发生在CancellationToken的ThrowIfCancellationRequested方法之后)。 代码: try { Parallel.For(0, 5, (i) => { throw new Exception("异常。迭代数字:" + i); }); } catch (Aggreg... 阅读全文
.NET(C#):DebuggerDisplay特性碉堡了!
摘要: 这个特性太碉堡了,很像WPF中的数据绑定,当然本质就是Visual Studio在调试时利用反射获取对象的值。 构造函数中的属性值(就是{}中的内容)不仅仅可以是简单的属性值。还可以是索引器,而且这一切可以嵌套。 (DebuggerDisplay特性(DebuggerDisplayAttribute类型)在System.Diagnostics命名空间内) 来定义一个有DebuggerDisplay的类: [DebuggerDisplay("第一个字符串:{List[0]},第一个字符串长度:{List[0].Length},第一个字符串中的第二个字符:{Lis... 阅读全文
.NET(C#) TPL:ParallelLoopState的Break方法和LowestBreakIteration属性
摘要: 首先当Break被调用后,循环中当前调用Break的执行后的迭代就没有必要去执行了,由于并行执行打乱了执行顺序,所以这个时候很可能某些不需要执行的迭代已经执行完了,这个没办法(也没必要)去取消它,当然调用Break后没有必要执行且没有开始执行的迭代最终不会被执行。 上面只讨论了“已经执行完”和“没有执行的状况”,对于正在执行的却没有必要执行的迭代,同样没办法将他停止,此时ParallelLoopState.LowestBreakIteration(类型是long?,默认是null)则会成为最小的调用Break的迭代索引。 来看第一个例子,我们从1-20命令他迭代20次,但是如果... 阅读全文
.NET(C#):警惕PLINQ结果的无序性
摘要: PLINQ的运行结果是无序的,也就是不保持原来集合的顺序来操作(当然除了一些专门的排序操作)。原因则是线程的并发执行本来就充满了不确定性,把原来一个任务分割成好几个部分同时进行返回的结果会打乱原来的顺序,如果要强制保留顺序,肯定要浪费一些性能,PLINQ是可以这样的,但默认不这样。 先看一个LINQ示例: var arr = new int[] { 1, 2, 3, 4, 5 }; var res = arr.Where(i => i != 3); 结果是: 1, 2, 4, 5 顺序是保持的。而PLINQ: var res = ar... 阅读全文
.NET(C#):DLR有趣的调用自己的动态对象
摘要: 一个动态对象竟然支持自己调用自己,根据MSDN的解释,此项功能仅在C#中被支持,VB并不可以。具体过程则是改写动态对象(DynamicObject类)的TryInvoke方法。和普通函数调用的TryInvokeMember方法类似。TryInvoke的第一个参数是Binder:InvokeBinder。但是和TryInvokeMember的InvokeMemberBinder不一样,它没有Name属性,因为对象自己调用自己自然没有方法名称。其他属性不需要多说明,CallInfo代表调用信息。ReturnType表示返回类型(继承自DynamicMetaObjectBinder)。 下面... 阅读全文
一个更人性化的Visual Studio的propfull属性字段Code Snippets
摘要: 今天要写一个支持序列化的类,因此需要手动写许多属性和字段,而不能使用C# 3.0后的自动属性。于是用到了Visual Studio的propfull Code Snippets,但是这个Code Snippets很不方便,如下: 有两大不好的地方: 属性名称和字段名称要定义两遍。我觉得字段名称直接在属性名称前自动加一个”_”就可以了。 set没有添加修饰符的支持。 为此我定义了另一个Code Snippet:propfull2 克服了上述缺点。属性类型和propfull一样。然后只需要指定一个名称,字段名称会自动在前面加”_”,然后可以指定set... 阅读全文
博客导读
摘要: 主要目录 按主要研究框架: 按类型(不包括界面和显示相关) 按类型(界面和显示相关) 其他 博客Tag 返回目录按主要研究框架: .NET Framework基础类库(BCL) Windows Presentation Foundation(WPF) Windows Runtime(WinRT) Windows Phone 和 Silverlight返回目录按类型(不包括界面和显示相关) 安全 反射 System.Diagnostics命名空间 进程 CLR和IL 程序集 Win32/Windows API 集... 阅读全文
WPF:通过可视状态(Visual State)定义控件的Validation.ErrorTemplate模板
摘要: 在.NET 4.0之前,定义数据绑定的验证错误模板只能通过Validation.ErrorTemplate附加属性。模板的具体定义也很不舒服,大体上是定义一个没有TargetType的ControlTemplate,然后在模板中加入AdornedElementPlaceholder。由于模板是在装饰器层中显示,所以对控件布局的设置局限性很大。 在.NET 4.0后有了可视状态(Visual State)前来支援,这个概念早在Silverlight 3中就有,后来才被加到WPF中的。 我们定义一个TextBox的错误模板,当数据绑定验证错误发生时,错误信息会动画出现: ... 阅读全文
WPF:各种缓动函数(Easing Function)动画预览切换
摘要: 写了一个小程序,用来演示WPF中的各种缓动函数(Easing Function)动画类型。 用户可以选择动画类型,包含所有WPF 4.0定义的类型: BackEase, BounceEase, CircleEase, CubicEase, ElasticEase, ExponentialEase, PowerEase, QuadraticEase, QuarticEase, QuinticEase, SineEase 缓动模式(即EasingMode枚举): EaseIn, EaseOut, EaseInOut 原理则是在资源中定义好Sto... 阅读全文
WPF:设置DataGrid中DataGridColumn列的普通样式和编辑样式
摘要: 目录 0:DataGridColumn类型的继承树 1:设置DataGridBoundColumn 2:设置DataGridComboBoxColumn 3:设置DataGridTemplateColumn 返回目录 0:DataGridColumn类型的继承树 DataGridColumn的派生类: 一般情况下DataGridBoundColumn和DataGridComboBoxColumn足以满足多数列的样式,如果需要自定义列样式,则可以使用DataGridTemplateColum... 阅读全文
|
|
|