Happy Spring Festival

相传,中国古时候有一种叫”年”的怪兽,头长触角,凶猛异常。”年”长年深居海底,每到除夕才爬上岸,吞食牲畜伤害人命。因此,每到除夕这天,村村寨寨的人们扶老携幼逃往深山,以躲避”年”兽的伤害。

怪兽---“年”

这年除夕,桃花村的人们正扶老携幼上山避难,从村外来了个乞讨的老人,只见他手拄拐杖,臂搭袋囊,银须飘逸,目若朗星。乡亲们有的封窗锁门,有的收拾行装,有的牵牛赶羊,到处人喊马嘶,一片匆忙恐慌景象。这时,谁还有心关照这位乞讨的老人。

只有村东头一位老婆婆给了老人些食物,并劝他快上山躲避”年”兽,那老人捋髯笑道:”婆婆若让我在家呆一夜,我一定把”年”兽撵走。老婆婆惊目细看,见他鹤发童颜、精神矍铄,气宇不凡。可她仍然继续劝说,乞讨老人笑而不语。婆婆无奈,只好撇下家,上山避难去了。

半夜时分,”年”兽闯进村。它发现村裏气氛与往年不同:村东头老婆婆家,门贴大红纸,屋内烛火通明。”年”兽浑身一抖,怪叫了一声。”年”朝婆婆家怒视片刻,随即狂叫著扑过去。将近门口时,院内突然传来”砰砰啪啪”的炸响声,”年”浑身战栗,再不敢往前凑了。

原来,”年”最怕红色、火光和炸响。这时,婆婆的家门大开,只见院内一位身披红袍的老人在哈哈大笑。”年”大惊失色,狼狈逃蹿了。

第二天是正月初一,避难回来的人们见村裏安然无恙十分惊奇。这时,老婆婆才恍然大悟,赶忙向乡亲们述说了乞讨老人的许诺。

乡亲们一齐拥向老婆婆家,只见婆婆家门上贴著红纸,院裏一堆未燃尽的竹子仍在”啪啪”炸响,屋内几根红腊烛还发著余光…欣喜若狂的乡亲们为庆贺吉祥的来临,纷纷换新衣戴新帽,到亲友家道喜问好。这件事很快在周围村裏传开了,人们都知道了驱赶”年”兽的办法。

从此每年除夕,家家贴红对联、燃放爆竹;户户烛火通明、守更待岁。初一一大早,还要走亲串友道喜问好。这风俗越传越广,成了中国民间最隆重的传统节日。
最后还是祝大家春节快乐 🙂

新春快乐

中文:春节愉快
港台:春節愉快
英文:Happy Spring Festival
日文:幸せなスプリング?フェスティバル
荷兰:Gelukkige Festival van de Lente
德语:Glückliches Frühling Festival
法语:Festival Heureux De Ressort
意大利:Festival Felice Della Molla
俄语:Счастливое Празднество Весны!
葡萄牙:Festival Feliz Da Mola

System.Transactions:实现你自己的Resource Manager

System.Transactions:实现你自己的Resource Manager

By Sahil Malik

.net 2.0所带来最大的变化之一也许就是System.Transactions命名空间的引入。在我以前关于SQLCLR的文章中,也简略的提到过这个命名空间。但是谁说事务的概念只能局限于数据库?难道我们在数据库以外的领域就不需要可靠的代码了么?答案是,我们当然需要! 这正是你不能忽视System.Transactions命名空间的原因,也是她将在下一代微软平台引起深刻变革的原因。让我们首先来看看 System.Transactions是如何工作的。

System.Transactions如何工作?

System.Transactions为您提供最简洁明了的方式来实现事务方式的各种操作。你当然可以用各种各样的方式使用她,但也许最典型的一个实现就是如下,将事务操作包裹在TransactionScope(用来构建代码段事务的一个实例变量)里面:

using (TransactionScope ts = new TransactionScope())
{
// 事务代码放这里
ts.Complete();
}

在上面注释的部分里面,你可以使用持有或实现了resource manager(RM)的类。

事务工作于各种被RM管理着的资源上。RM同其他实体(典型的包括:其他进程或者被称为transaction managers(TMs)的服务)协同工作。

RM与TM在事务中协同工作的方式常被称为”两段提交过程”。

下面是典型的“两段提交过程”工作流:

1.RM加入事务;
2.RM做完准备工作后,向TM发送第一阶段完成信号。这个阶段也被称为”准备阶段”;
3.TM在所有RMs成功执行完准备工作后,向所有RMs发送绿灯信号;
4.RMs获得绿灯信号后实际开始提交工作(如果收到红灯信号,则回滚他们自己的工作)。这是第二个阶段–“提交阶段”;
5.否则,事务协调器同所有RMs进行协调以保证他们要么成功,要么一起回滚;

上面提到的整个过程都由System.Transactions框架提供,例如,使用MSDTC(Microsoft分布式事务协调器)作为TMs。为了使用System.Transactions来管理参与事务操作的资源,你必须要么使用现有的RM或者实现你自己的RM。

就目前而论, System.Transactions已可以使用,但实际能应用的RMs却很少,所以很多程序员可能会发现实现自己的RM非常有用。在这之后,可以将这些RMs同未来.net框架中或第三方提供的TM协同工作。另外,同.net 2.0一同发布的一个很常用的RM就是SqlConnection类。本文中会以此类和一个自定义的RM为例,描述它们究竟如何同TM一起工作。但是,如果你确实不得不实现自己的RM,最重要的问题恐怕就是–“RM究竟要做些什么?”

RM究竟要做些什么?

影响实现你自己的RM的一个关键问题就是:这个RM管理的资源本身的特性是持久的还是易变的?

在典型的”两段提交过程”中,持久的资源需要”失败恢复”。一个很好的例子就是事务文件拷贝。如果你不得不实现一个RM来封装拷贝文件的操作到一个事务中,文件可以在第一个阶段被实际拷贝。如果RM失败,恢复策略将保证在回滚过程中,TM有足够的信息来恢复原来的状态。具体来说,可能就是指删除文件或者用以前存在的文件来代替。这种资源的收集操作,使用System.Transactions.Transaction.EnlistDurable方法。

反之,易变资源是不需要”失败恢复”的。同样一个很好的例子,就是持有在内存中的数据。封装这类操作到事务中的RM使用System.Transactions.Transaction.EnlistVolatile方法。

另外一种收集资源的方式是PSPE(可提升的单段式收集)。这种方式由持久的RM拥有事务,当条件改变时,可以逐步升级为由TM管理。因为持久的资源收集比易变的资源收集代价更大,PSPE提供了一种很有吸引力的持久资源收集的实现方式,但是这种方式在许多地方是以牺牲性能为代价的。

在选好资源收集的方式后,接下来你需要实现IEnlistmentNotification接口,以使你从TM获得必要的回调来进行恰当的提交或回滚。 Windows平台的TMs的例子是适合易变资源收集的LTM(轻量级的事务管理器)以及适合分布式或者持久资源收集的MSDTC。

话不多说,下面的例子将向你示范如何实现这些概念。

使用易变资源收集方式实现RM

下面的例子示范了在事务中写成员变量的RM:

public class VolatileRM : IEnlistmentNotification
{
private int memberValue = 0;
private int oldMemberValue = 0;
public int MemberValue
{
get { return memberValue; }
}
public void SetMemberValue(int newMemberValue)
{
Transaction currentTx = Transaction.Current;
if (currentTx != null)
{
Console.WriteLine("VolatileRM: SetMemberValue - EnlistVolatile");
currentTx.EnlistVolatile(this, EnlistmentOptions.None);
}
oldMemberValue = memberValue;
memberValue = newMemberValue;
}
IEnlistmentNotification Members#region IEnlistmentNotification Members
public void Commit(Enlistment enlistment)
{
Console.WriteLine("VolatileRM: Commit");
// Clear out oldMemberValue
oldMemberValue = 0;
}
public void InDoubt(Enlistment enlistment)
{
Console.WriteLine("VolatileRM: InDoubt");
}
public void Prepare(PreparingEnlistment preparingEnlistment)
{
Console.WriteLine("VolatileRM: Prepare");
preparingEnlistment.Prepared();
}
public void Rollback(Enlistment enlistment)
{
Console.WriteLine("VolatileRM: Rollback");
// Restore previous state
memberValue = oldMemberValue;
oldMemberValue = 0;
}
}

正如你所看到的那样,我们在SetMemberValue中首先检查了现在是否在事务中。如果是的话,它如下所示,将自己收集进易变事务中,并且为可能的回滚做一些必要的操作:

public void SetMemberValue(int newMemberValue)
{
Transaction currentTx = Transaction.Current;
if (currentTx != null)
{
Console.WriteLine("VolatileRM: SetMemberValue - EnlistVolatile");
currentTx.EnlistVolatile(this, EnlistmentOptions.None);
}
oldMemberValue = memberValue;
memberValue = newMemberValue;
}

示例中也实现了一系列其他的方法。提交(Commit)、回滚(RollBack),顾名思义,要么提交工作,要么回滚工作。TM调用Prepare方法来通知RM它正请求第一阶段的事务提交工作,并且测试你的RM是否为工作做好了准备。这里,你有下面三种选择:

1.调用preparingEnlistment.Prepare()方法。

这通知TM你已做好准备,并且正等待下一步提交的通知。

2.调用preparingEnlistment.ForceRollBack()方法或者指定preparingEnlistment.RecoveryInformation。

在重新收集资源的时候,这将提供新的RM实例和完成恢复工作所需要的充足的信息。但是现在你还不必为此担心。

3.调用preparingEnlistment.Done()方法。

这将RM作为旁观者。只观察事务,但并不参与其中。通过调用Done方法,TM不会给你第二阶段的通知。

既然你已经建好了RM,你现在能够依赖框架来编写简单可靠的代码。使用上面的RM是相当轻松惬意的一件事情。例如,键入下面的代码:

VolatileRM vrm = null ;
using (TransactionScope txSc = new TransactionScope())
{
vrm = new VolatileRM();
vrm.SetMemberValue(3);
txSc.Complete();
}
Console.WriteLine("Member Value:" + vrm.MemberValue);

上面代码产生下面的输出:

VolatileRM: SetMemberValue - EnlistVolatile
VolatileRM: Prepare
VolatileRM: Commit
Member Value:3

如你所见,成员值被更新了,并且RM在准备和提交阶段得到了相应的通知。

如果你想通过RM实现强制回滚,你可以如下简单的修改RM的Prepare方法:

public void Prepare(PreparingEnlistment preparingEnlistment)
{
Console.WriteLine("VolatileRM: Prepare");
preparingEnlistment.ForceRollback();
}

这将引起如下异常:

The Transaction Has Aborted.

事实上,你可以通过适当的preparingEnlistment.RollBack重载方法引起自定义的异常。

另外一种引起回滚的方法是简单的删掉TransactionScope.Complete语句或者在同一个事务中收集其他引起回滚的RM。

VolatileRM vrm = null ;
using (TransactionScope txSc = new TransactionScope())
{
vrm = new VolatileRM();
vrm.SetMemberValue(3);
// txSc.Complete();
}
Console.WriteLine("Member Value:" + vrm.MemberValue);

当你运行这段代码的时候,将产生如下输出:

VolatileRM: SetMemberValue - EnlistVolatile
VolatileRM: Rollback
Member Value: 0

你可能觉得这个范例有点不知所云。其实,你通过这个范例可以看到,你能够如此有效的创建与其他RM协同工作的事务代码。例如,你能够将这个非数据库操作的修改成员变量的操作同数据库的事务操作放在同一个事务中。你能够使用如下的T-SQL代码轻松建立数据库:

Create Database Test
Go
Create Table Demo
(
DemoValue varchar(5)
)

然后通过下面的代码将VolatileRM和两个SqlConnection实例收入同一个事务中:

private static string connStr = "Data Source=(local);Initial Catalog=Test;Integrated Security=True";
static void Main(string[] args)
{
VolatileRM vrm = null ;
using (TransactionScope txSc = new TransactionScope())
{
vrm = new VolatileRM();
vrm.SetMemberValue(3);
using (SqlConnection cn = new SqlConnection(connStr))
{
SqlCommand cmd = cn.CreateCommand();
cmd.CommandText = "Insert into Demo(DemoValue) Values ('XXX')";
cn.Open();
cmd.ExecuteNonQuery();
cn.Close();
}
using (SqlConnection cn = new SqlConnection(connStr))
{
SqlCommand cmd = cn.CreateCommand();
cmd.CommandText = "Insert into Demo(DemoValue) Values ('YYY')";
cn.Open();
cmd.ExecuteNonQuery();
cn.Close();
}
Console.WriteLine( "Transaction identifier:" + Transaction.Current.TransactionInformation.DistributedIdentifier);
txSc.Complete();
}
Console.WriteLine("Member Value:" + vrm.MemberValue);
}

框架能够通过PSPE自动识别出你的SqlConnection实例已经参与到事务中。当第二个SqlConnection实例出现时,它将在第二个 cn.Open方法被调用时自动将事务提升至MSDTC。你能够通过”控制面板->管理工具->组件服务”中观察这些操作:

提示: 连接至SQL Server 2005的SqlConnection采用PSPE方式,而连接至SQL Server 2000或更低版本的SqlConnection将采用持久方式,即使在当前事务中仅有一个RM。

当你运行程序时,产生如下输出:

VolatileRM: SetMemberValue - EnlistVolatile
Transaction identifier:c40015f6-5086-4688-b565-c65db1cbc8e7
VolatileRM: Prepare
VolatileRM: Commit
Member Value:3

如你所见,你依然在收集易变资源。但是,如果需要,你的事务将自动提升至MSDTC,并且获得分布式ID。如果你是架构师,这将给予你两个最好的世界:事务集成和可能最好的性能。你获得这些仅仅需要写如下的简单的代码:

Transaction
{
Operation A ;
Operation B ;
....
....
Commit();
}

实现基于System.Transactions的事务

现在你已经具备了基于System.Transactions实现事务处理的基础知识。你学到了各种各样的将资源收集到当前事务中的方法,并且看到了自定义RM收集易变资源是多么的简单。

下载代码

下载相关代码,点击这里

关于作者

Sahil Malik熟悉从Dos至.Net等许多尖端的微软科技。他是Pro ADO.NET 2.0的作者以及Pro ADO.NET with VB.NET 1.1的合著者。Sahil目前也在基于ADO.NET 2.0的多媒体领域有所建树。他曾被授予微软MVP称号。

中国九大令人寒心的冷笑话

1.秦始皇修筑万里长城时死了许多人,孟姜女的丈夫万喜良也在其中。听到这个消息,孟姜女只觉得天昏地暗,一下子昏倒在地,醒来后,她伤心地痛哭起来,只哭得天愁地惨,日月无光。不知哭了多久,忽听得天摇地动般地一声巨响,长城崩塌了几十里,露出了数不清的尸骨。孟姜女咬破手指,把血滴在一具具的尸骨上,她心里暗暗祷告:如果是丈夫的尸骨,血就会渗进骨头,如果不是,血就会流向四方。终于,孟姜女用这种方法找到了万喜良的尸骨。她抱着这堆白骨,哭着说道: “老万,你的死跟你丫本人素质不高有关啊!”

—11月30日,七煤公司一领导在接受采访时表示,“11·27”矿难的主要原因归咎于井下矿工对规章制度执行不力,劳动者的素质离我们的要求还差很远。

2、武松醉打蒋门神、替施恩夺了快活林之后,中了张都监、张团练的计,几乎命丧飞云浦。武松杀了张都监的几名爪牙,寻思了半晌,怨恨冲天:“不杀得张都监,如何出得这口恨气!”便去死尸身边解下腰刀,选好的取把将来跨了,拣条好朴刀提着,直奔孟州城张都监的后花园。张都监、张团练、蒋门神正在鸳鸯楼吃酒,冷不防武松闯了进来,噗噗几刀砍死蒋门神、张团练。武松踏着张都监的脑袋喝道:“你们这帮贼子,为何黑道白道勾结、串通一气害我?”张都监颤颤巍巍地答道:“说句实话,官匪勾结的重要原因,是我们的待遇过低了!”

—成都火车站派出所副所长付小华接受采访时表示:“出现‘警匪勾结’这种情况的重要原因是pol.ice待遇过低”

3、董存瑞牺牲后到了天堂,上帝问他:“你是怎么死的?”董存瑞说:“为了炸敌人的碉堡,被de-tona-tor包炸死的”上帝听后勃然大怒,说道:“胡说!你胆敢骗我?”
董存瑞说:“我没骗您啊!”上帝说:“你以为我不懂科学吗?谁不知道,爆炸只会产生水和二氧化碳,你不是被水淹死的、就是被二氧化碳薰死的,怎么可能是被炸死的呢?!”

—吉林石化的人所说:爆炸产生水和二氧化碳,不会污染水源

4、孔子路过泰山脚下,有一个妇女在墓前哀伤地哭泣。孔子手扶车沿听她哭诉,并让**问她缘由,妇女说:“以前我的公公被老虎咬死,我的丈夫跟着被老虎咬死,现在我的儿子也被老虎咬死了;”孔子说:“事情都过去了,又何必伤心?那为什么不离开这里呢?”
妇女说:“我怕失去低收入者作为纳税人的荣誉!”孔子于是对**道:“小子识之,苛政虽猛于虎,然纳税人的荣誉牛X于苛政也!”

—全国人大农业与农村委员会委员任正隆则认为,起征点太高剥夺了低收入者作为“纳税人”的荣誉。

5、汉朝的淮南王刘安派人进山访仙,从仙翁手里得到了一张仙方。他把自己关进暗房里,炼起仙丹来。八卦炉里炼出一些圆滚滚的仙丹,他一口气吞下5颗,飘飘悠悠飞上天去了!门外的鸡犬一看,也跟着大吃起来,不一会,空中一阵鸡鸣狗叫,原来它们也飞上天了!有人问道:“刘安,你家的鸡犬怎么也跟着成仙了?”刘安说:“为了防止拉登发动KB袭击、撞击天庭,我特意实行“一人得道,鸡犬升天”制,在任何紧急情况下,都能及时帮助疏散与救援,这是一个安全上的举措,并不是专门把成仙作为福利”。

—广州地铁线网听政会上,地铁员工家属免费坐地铁引起代表争议,地铁总经理解释,是为了“反恐需要”。

6、三国演义里,诸葛亮造木牛流马,用来运送粮草,以此大败曹军。但后来木牛流马却失传了,即便是诸葛亮的得意**姜维也不会造。诸葛军师临终前众将问他:“军师,木牛流马这般好用,为何您再也不造了?”孔明长叹一声曰:“某交通学大学士、大教授的研究结果表明,木牛流马的污染比汽车飞机大,为了子孙后代的幸福,你还是等着坐汽车吧!”

—“中国城市环境污染不是由汽车造成的,而是由自行车造成的”。国内一家搞环境研究的权威机构经过一番调查与研究后得出的一个“科学”结论。

7、老栓也向那边看,却只见一堆人的后背;颈项都伸得很长,仿佛许多鸭,被无形的手捏住了的,向上提着。静了一会,似乎有点声音,便又动摇起来,轰的一声,都向后退;一直散到老栓立着的地方,几乎将他挤倒了。“喂!一手交钱,一手交货!”一个浑身黑色的人,站在老栓面前,眼光正像两把刀,刺得老栓缩小了一半。那人一只大手,向他摊着;一只手却撮着一个鲜红的馒头,那红的还是一点一点的往下滴。老栓慌忙摸出洋钱,抖抖的想交给他,却又不敢去接他的东西。那人便焦急起来,嚷道,“怎么?嫌贵?舍不得银子?”老栓还踌躇着,黑的人便抢过灯笼,一把扯下纸罩,裹了馒头,塞与老栓;一手抓过洋钱,捏一捏,转身去了。嘴里哼着说:“这血馒头是药,不能当馒头卖!价格不贵,不同意降价!”

—“药品怎么能当馒头卖?”在“看病难,药价贵”呼声高涨时,东盛制药集团总裁陶朝辉却反其道而行之,抛出“馒头论”,坚持“药价不贵,不同意降价”。

8、宋代穷儒陈世美,进京考中状元,被招为驸马。其发妻秦香莲带二子上京寻亲,陈世美翻脸不认人;秦香莲悲痛欲绝,发誓要讨还情债。陈世美勃然大怒,上表朝廷奏曰:臣以为,开封自古就是神圣之地,岂容外地人随便进入?应该建立人口准入制度!同时,对那些恶意讨情之人,应坚决打击!”

—在刚刚结束的北京市“两会”上,政协委员张惟英教授提出“建立人口准入制度”的建议:目前北京市的居住人口已超过各种资源的人口承载极限,严重制约了北京的发展,建议摸清北京市实际需要的人才类别,用准入制度进行合理的引入,规范人口流动。

9、有一日,窦娥碰到苏三、杨乃武、小白菜等人,就问他们:“你们都平反昭雪了吗?”众人说:“都昭雪了”;窦娥又问: “那少奇兄弟、德怀兄弟、志新妹妹呢?”众人说:“也都平反了”。窦娥便道:“我说什么来着,咱们的司法就是公正!那么多案件从错的纠成正的,这难道不是司法公正的体现吗?”

—被无辜关押11年的佘祥林被宣告无罪了,但这一悲剧投石入湖的震荡,远远没有平息。当事人申请国家赔偿、责任人被追究法律责任,尚都在公众的持续关注中。种种怨怒未消之下,另一方面却居然频频出现奇怪的言论:4月1日湖北高院向该省法院系统发出通知,要求认真总结避免佘祥林被冤杀的经验;最高法副院长万鄂湘日前在就此案答媒体问时又说:“是否司法不公应该从最后纠正的结果看。这个案件从错的又纠成正的,难道不是司法公正的体现吗?”