[JavaScript]BlackBird开源调试框架

mikel阅读(796)

Blackbird 是一个开源的JavaScript库,提供了一种简单的记录日志的方式和一个控制台窗口,有了这个之后,你就可以抛弃alert() 了。支持下面的浏览器:

* Internet Explorer 6+
* Firefox 2+
* Safari 2+
* Opera 9.5

另外,如果你使用的是YUI的话,可以考虑YUI中的Logger组件

[SQL]SQL Server中小心使用@@identity

mikel阅读(948)

@@identity的作用是返回最后插入的标识值,所以有很多朋友使用它来获取插入数据后的标识符。
但有一点是需要注意的,@@identity返回的是最后的标识符,所以,要想正确的返回插入后的标识符,那么就必须保证,你想要的结果是最后的标识符,否则就会隐藏bug。
仔细阅读@@identity的注释:

注释

在一条 Insert、Select INTO 或大容量复制语句完成后,@@IDENTITY 中包含此语句产生的最后的标识值。若此语句没有影响任何有标识列的表,则 @@IDENTITY 返回 NULL。若插入了多个行,则会产生多个标识值,@@IDENTITY 返回最后产生的标识值。如果此语句激发一个或多个执行产生标识值的插入操作的触发器,则语句执行后立即调用 @@IDENTITY 将返回由触发器产生的最后的标识值。若 Insert 或 Select INTO 语句失败或大容量复制失败,或事务被回滚,则 @@IDENTITY 值不会还原为以前的设置。

在返回插入到表的 @@IDENTITY 列的最后一个值方面,@@IDENTITY、SCOPE_IDENTITY 和 IDENT_CURRENT 函数类似。

@@IDENTITY 和 SCOPE_IDENTITY 将返回在当前会话的所有表中生成的最后一个标识值。但是,SCOPE_IDENTITY 只在当前作用域内返回值,而 @@IDENTITY 不限于特定的作用域。

例如:创建表t和t1

drop table t
drop table t1

create table t 
(
id 
int identity(1,1)primary key,
name 
char(10)
)
create table t1 
(
id 
int identity(10,1)primary key,
name 
char(10)
)

创建表t的触发器,作用是当有新的数据插入到表t时,t1也相应的插入一条数据。

触发器
create trigger trigger_insert on t
for insert
as
insert into t1(name) select name from inserted

然后,执行执行如下语句:

insert into t(name) values('me')
select @@identity

这时候,你期望得到的结果是1,但其实返回的结果却是10。
使用时,这就是你要注意的问题啦。
论坛支持:www.help-doc.com
相关知识可以参考:http://www.help-doc.com/17/ShowForum.aspx
SQL Server 2005的帮助中的内容:

SCOPE_IDENTITY、IDENT_CURRENT 和 @@IDENTITY 是相似的函数,因为它们都返回插入到标识列中的值。

IDENT_CURRENT 不受作用域和会话的限制,而受限于指定的表。IDENT_CURRENT 返回为任何会话和作用域中的特定表所生成的值。有关详细信息,请参阅 IDENT_CURRENT (Transact-SQL)

SCOPE_IDENTITY 和 @@IDENTITY 返回在当前会话中的任何表内所生成的最后一个标识值。但是,SCOPE_IDENTITY 只返回插入到当前作用域中的值;@@IDENTITY 不受限于特定的作用域。

例如,有两个表 T1 和 T2,并且在 T1 上定义了 Insert 触发器。当将某行插入 T1 时,触发器被激发,并在 T2 中插入一行。 该方案演示了两个作用域:在 T1 上的插入,以及在 T2 通过触发器的插入。

假设 T1 和 T2 都有标识列,@@IDENTITY 和 SCOPE_IDENTITY 将在 T1 上的 Insert 语句的最后返回不同的值。@@IDENTITY 将返回在当前会话中的任何作用域内插入的最后一个标识列的值。这是在 T2 中插入的值。SCOPE_IDENTITY() 将返回在 T1 中插入的 IDENTITY 值。这是在同一个作用域内发生的最后的插入。如果在任何 Insert 语句作用于作用域中的标识列之前调用 SCOPE_IDENTITY() 函数,则该函数将返回空值。

如果语句和事务失败,它们会更改表的当前标识,从而使标识列中的值出现不连贯现象。即使未提交试图向表中插入值的事务,也永远无法回滚标识值。例如,如果因 IGNORE_DUP_KEY 冲突而导致 Insert 语句失败,表的当前标识值仍然会增加。

[C#]ADO.Net执行存储过程

mikel阅读(724)

存储过程————————————————————————————————


Create PROCEDURE dbo.sptestList

@strOptions varchar(
200= NULL,
@intID 
int = NULL,
@strOut nvarchar(
50= NULL   OUTPUT

AS

SET NOCOUNT ON
不返回影响的行数
SET ANSI_WARNINGS OFF
不返警告

/* 信息列表 */
IF @strOptions
='LIST' BEGIN

Select
   id,
   name,
   subject,
   Source
FROM test 
Where ID 
<=@intID

SET @strOut 
= @strOut + 'out'
RETURN 
50
END
GO


————————————————————————-

//StoredProcedure 调用存储过程
    private void BindData2()
    
{
        SQLConnection MyConn 
= new SQLConnection("Server=.;Database=mine;User=sa;Pwd=123;");
        MyConn.Open();

        SqlCommand MyCmd 
= new SqlCommand();
        MyCmd.Connection 
= MyConn;
        MyCmd.CommandType 
= CommandType.StoredProcedure;
        MyCmd.CommandText 
= "sptestList";
        
string strOut = "in—";
        
int intReturn = 0;

        SqlParameter[] paras 
= 
            
{
                
new SqlParameter("@strOptions","LIST"),
                
new SqlParameter("@intID",100),
                
//长度一定需要
                new SqlParameter("@strOut",SqlDbType.VarChar,200),
                
//用来存返回值,ReturnValue随便写都可以,但类型一定是整型(因为数据库只能返回整型)
                new SqlParameter("ReturnValue",SqlDbType.Int)
            
            }
;
      
        paras[
2].Direction = ParameterDirection.InputOutput;//设置 传入并传出
        paras[2].Value = strOut;
        paras[
3].Direction = ParameterDirection.ReturnValue;//设置 返回值


        
foreach (SqlParameter par in paras)
        
{
            MyCmd.Parameters.Add(par);
        }


        SqlDataAdapter MySda 
= new SqlDataAdapter(MyCmd);
        DataTable MyDtb 
= new DataTable();
        MySda.Fill(MyDtb);

        strOut 
= paras[2].Value.ToString();//接收传出
        intReturn = (int)paras[3].Value;//接收返回值
        Response.Write("Out=" + strOut + "; Return=" + intReturn.ToString() + "<br>");

        
this.Repeater1.DataSource = MyDtb;
        
this.Repeater1.DataBind();

        MyConn.Close();

    }


    
//SqlDataAdapter 执行查询语句
    private void BindData()
    
{
        SqlConnection MyConn 
= new SqlConnection("Server=.;Database=mine;User=sa;Pwd=123;");

        SqlCommand MyCmd 
= new SqlCommand("Select TOP 100 * FROM Test", MyConn);
        SqlDataAdapter MySda 
= new SqlDataAdapter(MyCmd);
        DataTable MyDtb 
= new DataTable();
        MySda.Fill(MyDtb);

        
this.Repeater1.DataSource = MyDtb;
        
this.Repeater1.DataBind();

    }


    
//ExecuteNonQuery 执行插入语句
    protected void FInsert()
    
{
        SqlConnection MyConn 
= new SqlConnection("Server=.;DataBase=mine;Uid=sa;Pwd=123;");

        SqlCommand MyCmd 
= new SqlCommand("Insert INTO StudentInfo(StNo,StName) VALUES(124532,'A111ww')", MyConn);
        MyConn.Open();
        
int i = MyCmd.ExecuteNonQuery();
        Response.Write(i.ToString() 
+ "<br>");
        MyConn.Close();

    }


    
//SqlDataReader
    protected void FReader()
    
{
        SqlConnection MyConn 
= new SqlConnection("Server=.;Database=mine;Uid=sa;Pwd=123");
        MyConn.Open();
        SqlCommand MyCmd 
= new SqlCommand("Select Top 10 StNo,StName from StudentInfo", MyConn);

        SqlDataReader MyRead 
= MyCmd.ExecuteReader();

        
while (MyRead.Read())
        
{
            Response.Write(MyRead[
"StNo"].ToString() + "" + MyRead["StName"].ToString() + "<br>");
        }


        MyConn.Close();

    }


    
//ExecuteScalar
    protected void FScalar()
    
{

        
//<appSettings>
        
//<add key ="SqlConnStr" value="Server=.;DataBase=mine;Uid=sa;Pwd=123"/>
        
//</appSettings>
        
//SqlConnection MyConn = new SqlConnection(ConfigurationManager.AppSettings["SqlConnStr"]);
        SqlConnection MyConn = new SqlConnection("Server=.;Database=mine;Uid=sa;Pwd=123");
        MyConn.Open();
        SqlCommand MyCmd 
= new SqlCommand("Select Total=Count(1) from StudentInfo", MyConn);

        
string MyS = MyCmd.ExecuteScalar().ToString();

        Response.Write(MyS 
+ "<br>");

        MyConn.Close();

    }


//连接Access
    private void BindAccess()
    
{
        
//<add key="AccessConString" value="App_Data/db.mdb" />
        string strAccessPath = ConfigurationManager.AppSettings["AccessConString"].ToString();
        OleDbConnection con 
= new OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" + Server.MapPath(strAccessPath));
        con.Open();
        OleDbDataAdapter oda 
= new OleDbDataAdapter("Select * From Result", con);
        DataTable Dtb 
= new DataTable();
        oda.Fill(Dtb);

        
this.Repeater1.DataSource = Dtb;
        
this.Repeater1.DataBind();

        
//———————-二—————————–
        
//string constr = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=" + Server.MapPath("App_Data/db.mdb");
        
//OleDbConnection con = new OleDbConnection(constr);
        
//string cmdstr = "Select * FROM Result";
        
//con.Open();
        
//OleDbCommand cmd = new OleDbCommand(cmdstr, con);
        
//OleDbDataReader dr = cmd.ExecuteReader();
    }



//OleDbCommand 执行语句
    protected void Button1_Click(object sender, EventArgs e)
    
{
        OleDbConnection con 
= new OleDbConnection("Provider=Microsoft.Jet.OleDb.4.0;Data Source="
            
+ Server.MapPath(ConfigurationManager.AppSettings["OleDbConnPathStr"]));
        con.Open();

        OleDbCommand cmd 
= new OleDbCommand("Insert Into Products(Product_Id,Title,Spec,Content) Values('ww123','成功添加01','100*1','真的成功了')", con);

        cmd.ExecuteNonQuery();

        con.Close();
        con.Dispose();

        BindData();

    }


    
//OleDbDataAdapter 读取数据
    protected void Button2_Click(object sender, EventArgs e)
    
{
        OleDbConnection con 
= new OleDbConnection("Provider=Microsoft.Jet.OleDb.4.0;Data Source="
            
+ Server.MapPath(ConfigurationManager.AppSettings["OleDbConnPathStr"]));
        con.Open();

        OleDbDataAdapter odad 
= new OleDbDataAdapter("Select * From Products Where ID=123", con);

        DataTable dtb 
= new DataTable();
        odad.Fill(dtb);

        
if (dtb.Rows.Count > 0)
        
{
            DataRow row 
= dtb.Rows[0];

            
this.Label.Text = row["ID"].ToString() + "" + row["Title"].ToString();
        }


        con.Close();
        con.Dispose();
    }


    
//OleDbCommand 执行语句(参数化)
    protected void Button3_Click(object sender, EventArgs e)
    
{
        OleDbConnection con 
= new OleDbConnection("Provider=Microsoft.Jet.OleDb.4.0;Data Source="
            
+ Server.MapPath(ConfigurationManager.AppSettings["OleDbConnPathStr"]));
        con.Open();

        OleDbCommand cmd 
= new OleDbCommand();
        cmd.Connection 
= con;
        cmd.CommandType 
= CommandType.Text;
        cmd.CommandText 
= "Insert Into Products(Product_Id,Title,Spec,Content) Values(@Product_Id,@Title,@Spec,@Content)";

        OleDbParameter[] paras 
= {
            
new OleDbParameter("@Product_Id",OleDbType.VarChar),
            
new OleDbParameter("@Title",OleDbType.VarChar),
            
new OleDbParameter("@Spec",OleDbType.VarChar),
            
new OleDbParameter("@Content",OleDbType.VarChar)
        }
;

        paras[
0].Value = "qq123";
        paras[
1].Value = "qq成功添加";
        paras[
2].Value = "10*10";
        paras[
3].Value = "qq真的成功了";

        
foreach (OleDbParameter para in paras)
        
{
            cmd.Parameters.Add(para);
        }


        cmd.ExecuteNonQuery();

        con.Close();
        con.Dispose();

        BindData();
    }

[C#]SqlCommand.ExecuteNonQuery返回值

mikel阅读(904)

当执行Update、Insert 和 Delete时,SQLHelper的ExecuteNonQuery方法能正确的返回受影响的行数,但执行Select时返回值却总是-1,今天上 MSDN查了下SQLCommand.ExecuteNonQuery方法,上边的解释是:

引用内容 引用内容
对于 Update、Insert 和 Delete 语句,返回值为该命令所影响的行数。对于所有其他类型的语句,返回值为 -1。如果发生回滚,返回值也为 -1。

那上述现象的出现就是正常的了,呵呵。
MSDN地址:http://msdn2.microsoft.com/zh-cn/library/system.data.sqlclient.sqlcommand.executenonquery(VS.80).aspx

[JQuery]JQuery事件总结

mikel阅读(758)

  很少写这些,看了1.2.3版本的改进,确实佩服,很方便.
1.绑定事件
(1)

$("p").bind("click", function(e){});

(2)

$("p").click(function() {})

2.删除事件
(1)删除特定事件

$("div").unbind("click");

(2)删除所有事件

$("div").unbind();

3.触发事件
(1)trigger方法 触发特定元素事件

$("div").trigger('click');

(2)triggerHandler方法 与trigger方法相似,但不触发浏览器默认事件,如focus事件,使用此方法,将会阻止焦点到元素上

$("input").triggerHandler("focus");

4.特殊事件
(1)one(string event,function data)
此事件只执行一次则被删除

$("p").one("click", function(){
   alert(
"test");
}
);

(2)hover(over, out)
切换mouSEOver与mouSEOut事件

$("td").hover(
   function ()
{
     $(
this).addClass("hover");
   }
,
   function ()
{
     $(
this).removeClass("hover");
   }

);

可用unbind mouseover与mouseout方法来删除此事件
(3)toggle(oldclick,newclick)
切换执行click事件

     $("li").toggle(
       function ()
{
         $(
this).css("list-style-type", "disc")
                .css(
"color", "blue");
       }
,
       function ()
{
         $(
this).css({"list-style-type":"", "color":""});
       }

     );

可用unbind click方法来删除此事件
5.     1.2.3版本新增功能
(1)事件命名空间(便于管理)
实际使用方面:
1.当不需要全部事件,删除特定2个以上的事件.
示例:

   $("div").bind("click.plugin",function() {} );
   $(
"div").bind("mouseover.plugin", function(){});
   $(
"div").bind("dblclick", function(){});
   $(
"button").click(function() {$("div").unbind(".plugin");   })

在事件名称后面加命名空间,在删除事件时,只需要指定命名空间即可.以上代码执行以后,dbclick仍然存在.
(2)相同事件名称,不同命名的事件执行方法
示例:

$("div").bind("click", function(){ alert("hello"); });
   $(
"div").bind("click.plugin", function(){ alert("goodbye"); });
   $(
"div").trigger("click!"); // alert("hello") only

以上trigger方法则根据事件名称来执行事件.
简单的写几句.以上的几个方法还是非常实用方便的

[原创]重复获得验证码的问题

mikel阅读(883)

验证码的页面可能由于验证码不清楚,单击需要获得新的验证码
服务器端用C#实现如下:

/// <summary>
/// 验证码类,用于生成验证码
/// </summary>
public static class ValidateCode
{
private static string Cr&#101;ateRandomCode(int codeCount)
{
string allChar = "0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,W,X,Y,Z";
string[] allCharArray = allChar.Split(&#39;,&#39;);
string randomCode = "";
int temp = -1;
Random rand = new Random();
for (int i = 0; i < codeCount; i++)
{
if (temp != -1)
{
rand = new Random(i * temp * ((int)DateTime.Now.Ticks));
}
int t = rand.Next(35);
if (temp == t)
{
return Cr&#101;ateRandomCode(codeCount);
}
temp = t;
randomCode += allCharArray&#91;t&#93;;
}
return randomCode;
}
public static MemoryStream Cr&#101;ateImage(out string checkCode)
{
//生成随机数
checkCode = Cr&#101;ateRandomCode(4);
int iwidth = (int)(checkCode.Length * 13.5);
System.Drawing.Bitmap image = new System.Drawing.Bitmap(iwidth, 20);
Graphics g = Graphics.FromImage(image);
Font f = new System.Drawing.Font("Arial", 12, System.Drawing.FontStyle.Bold);
Brush b = new System.Drawing.SolidBrush(Color.Black);
//g.FillRectangle(new System.Drawing.SolidBrush(Color.Blue),0,0,image.Width, image.Height);
g.Clear(Color.White);
g.DrawString(checkCode, f, b, 3, 3);
Pen blackPen = new Pen(Color.Black, 0);
Random rand = new Random();
for (int i = 0; i < 3; i++)
{
int y = rand.Next(image.Height);
g.DrawLine(blackPen, 0, y, image.Width, y);
}
MemoryStream ms = new MemoryStream();
image.Save(ms, System.Drawing.Imaging.ImageFormat.Jpeg);
g.Dispose();
image.Dispose();
return ms;
}
}
&#91;/code&#93;
使用Asp.net MVC实现的Controller调用验证码的Action如下:
没有生成中间gif,jpg文件
&#91;code&#93;
/// <summary>
/// 获得验证码
/// </summary>
public void GetValidateCode()
{
try
{
//生成验证码
string validateCode;
Session["ValidateCode"] = "";
//生成验证码图片
MemoryStream ms = ValidateCode.Cr&#101;ateImage(out validateCode);
ViewData["Code"] = ms;
//保存到Session
Session["ValidateCode"] = validateCode;
Response.ClearContent();
Response.ContentType = "image/Gif";
Response.BinaryWrite(ms.ToArray());
}
catch (Exception e)
{
Response.Write("验证码生成失败!错误消息:" + e.Message);
}
}

页面代码:

<script language="javascript" type="text/javascript">
//获得验证码
function GetCode()
{
//注意后面一定要加随机数,这样<img>才能更新为新的验证码
$("#validateImg").attr("src","/user/GetValidateCode?sd="+Math.random());
}
</script>
<a id="getCode" href="javascript:GetCode();"><img  id="validateImg"  src="/user/GetValidateCode"  alt="点击获得验证码" /></a>

[C#]C#中的序列化和反序列化

mikel阅读(837)

序列化和反序列化我们可能经常会听到,其实通俗一点的解释,序列化就是把一个对象保存到一个文件或数据库字段中去,反序列化就是在适当的时候把这个文件再转化成原来的对象使用。

  我想最主要的作用有:

  1、在进程下次启动时读取上次保存的对象的信息

  2、在不同的AppDomain或进程之间传递数据

  3、在分布式应用系统中传递数据

  ……

  在C#中常见的序列化的方法主要也有三个:BinaryFormatter、SoapFormatter、XML序列化

  本文就通过一个小例子主要说说这三种方法的具体使用和异同点

  这个例子就是使用三种不同的方式把一个Book对象进行序列化和反序列化,当然这个Book类首先是可以被序列化的。至于怎么使一个类可以序列化可以参见:C#强化系列文章一:ViewState使用兼谈序列化

  Book类

  using System;

  using System.Collections;

  using System.Text;

  namespace SerializableTest

  {

  [Serializable]

  public class Book

  {

  public Book()

  {

  alBookReader = new ArrayList();

  }

  public string strBookName;

  [NonSerialized]

  public string strBookPwd;

  private string _bookID;

  public string BookID

  {

  get { return _bookID; }

  set { _bookID = value; }

  }

  public ArrayList alBookReader;

  private string _bookPrice;

  public void SetBookPrice(string price)

  {

  _bookPrice = price;

  }

  public void Write()

  {

  Console.WriteLine("Book ID:" + BookID);

  Console.WriteLine("Book Name:" + strBookName);

  Console.WriteLine("Book Password:" + strBookPwd);

  Console.WriteLine("Book Price:" + _bookPrice);

  Console.WriteLine("Book Reader:");

  for (int i = 0; i < alBookReader.Count; i++)

  {

  Console.WriteLine(alBookReader[i]); [Page]

  }

  }

  }

  }

  这个类比较简单,就是定义了一些public字段和一个可读写的属性,一个private字段,一个标记为[NonSerialized]的字段,具体会在下面的例子中体现出来

  一、BinaryFormatter序列化方式

  1、序列化,就是给Book类赋值,然后进行序列化到一个文件中

  Book book = new Book();

  book.BookID = "1";

  book.alBookReader.Add("gspring");

  book.alBookReader.Add("永春");

  book.strBookName = "C#强化";

  book.strBookPwd = "*****";

  book.SetBookPrice("50.00");

  BinarySerialize serialize = new BinarySerialize();

  serialize.Serialize(book);2、反序列化

  BinarySerialize serialize = new BinarySerialize();

  Book book = serialize.DeSerialize();

  book.Write();3、测试用的

  BinarySerialize类

  using System;

  using System.Collections.Generic;

  using System.Text;

  using System.IO;

  using System.Runtime.Serialization.Formatters.Binary;

  namespace SerializableTest

  {

  public class BinarySerialize

  {

  string strFile = "c:\book.data";

  public void Serialize(Book book)

  {

  using (FileStream fs = new FileStream(strFile, FileMode.Create))

  {

  BinaryFormatter formatter = new BinaryFormatter();

  formatter.Serialize(fs, book);

  }

  }

  public Book DeSerialize()

  {

  Book book;

  using (FileStream fs = new FileStream(strFile, FileMode.Open))

  {

  BinaryFormatter formatter = new BinaryFormatter(); [Page]

  book = (Book)formatter.Deserialize(fs);

  }

  return book;

  }

  }

  }

  主要就是调用System.Runtime.Serialization.Formatters.Binary空间下的 BinaryFormatter类进行序列化和反序列化,以缩略型二进制格式写到一个文件中去,速度比较快,而且写入后的文件已二进制保存有一定的保密效 果。

  调用反序列化后的截图如下:

  也就是说除了标记为NonSerialized的其他所有成员都能序列化

  二、SoapFormatter序列化方式

  调用序列化和反序列化的方法和上面比较类似,我就不列出来了,主要就看看SoapSerialize类

  SoapSerialize类

  using System;

  using System.Collections.Generic;

  using System.Text;

  using System.IO;

  using System.Runtime.Serialization.Formatters.Soap;

  namespace SerializableTest

  {

  public class SoapSerialize

  {

  string strFile = "c:\book.soap";

  public void Serialize(Book book)

  {

  using (FileStream fs = new FileStream(strFile, FileMode.Create))

  {

  SoapFormatter formatter = new SoapFormatter();

  formatter.Serialize(fs, book);

  }

  }

  public Book DeSerialize()

  {

  Book book;

  using (FileStream fs = new FileStream(strFile, FileMode.Open))

  {

  SoapFormatter formatter = new SoapFormatter();

  book = (Book)formatter.Deserialize(fs);

  }

  return book;

  }

  }

  }

  主要就是调用System.Runtime.Serialization.Formatters.Soap空间下的SoapFormatter 类进行序列化和反序列化,使用之前需要应用 System.Runtime.Serialization.Formatters.Soap.dll(.net自带的)

  序列化之后的文件是Soap格式的文件(简单对象访问协议(Simple Object Access Protocol,SOAP),是一种轻量的、简单的、基于XML的协议,它被设计成在WEB上交换结构化的和固化的信息。 SOAP 可以和现存的许多因特网协议和格式结合使用,包括超文本传输协议(HTTP),简单邮件传输协议(SMTP),多用途网际邮件扩充协议(MIME)。它还 支持从消息系统到远程过程调用(RPC)等大量的应用程序。SOAP使用基于XML的数据结构和超文本传输协议(HTTP)的组合定义了一个标准的方法来 使用Internet上各种不同操作环境中的分布式对象。) [Page]

  调用反序列化之后的结果和方法一相同

  三、XML序列化方式

  调用序列化和反序列化的方法和上面比较类似,我就不列出来了,主要就看看XmlSerialize类

  XmlSerialize类

  using System;

  using System.Collections.Generic;

  using System.Text;

  using System.IO;

  using System.Xml.Serialization;

  namespace SerializableTest

  {

  public class XmlSerialize

  {

  string strFile = "c:\book.xml";

  public void Serialize(Book book)

  {

  using (FileStream fs = new FileStream(strFile, FileMode.Create))

  {

  XmlSerializer formatter = new XmlSerializer(typeof(Book));

  formatter.Serialize(fs, book);

  }

  }

  public Book DeSerialize()

  {

  Book book;

  using (FileStream fs = new FileStream(strFile, FileMode.Open))

  {

  XmlSerializer formatter = new XmlSerializer(typeof(Book));

  book = (Book)formatter.Deserialize(fs);

  }

  return book;

  }

  }

  }

  从这三个测试类我们可以看出来其实三种方法的调用方式都差不多,只是具体使用的类不同

  xml序列化之后的文件就是一般的一个xml文件:

  book.xml

  <?xml version="1.0"?>

  <Book xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">

  <strBookName>C#强化</strBookName>

  <strBookPwd>*****</strBookPwd>

  <alBookReader>

  <anyType xsi:type="xsd:string">gspring</anyType>

  <anyType xsi:type="xsd:string">永春</anyType>

  </alBookReader>

  <BookID>1</BookID>

  </Book>输出截图如下:

  也就是说采用xml序列化的方式只能保存public的字段和可读写的属性,对于private等类型的字段不能进行序列化

  关于循环引用:

  比如在上面的例子Book类中加入如下一个属性:

  public Book relationBook;

  在调用序列化时使用如下方法:

  Book book = new Book();

  book.BookID = "1"; [Page]

  book.alBookReader.Add("gspring");

  book.alBookReader.Add("永春");

  book.strBookName = "C#强化";

  book.strBookPwd = "*****";

  book.SetBookPrice("50.00");

  Book book2 = new Book();

  book2.BookID = "2";

  book2.alBookReader.Add("gspring");

  book2.alBookReader.Add("永春");

  book2.strBookName = ".NET强化";

  book2.strBookPwd = "*****";

  book2.SetBookPrice("40.00");

  book.relationBook = book2;

  book2.relationBook = book;

  BinarySerialize serialize = new BinarySerialize();

  serialize.Serialize(book);这样就会出现循环引用的情况,对于BinarySerialize和 SoapSerialize可以正常序列化(.NET内部进行处理了),对于XmlSerialize出现这种情况会报错:"序列化类型 SerializableTest.Book 的对象时检测到循环引用。"

[C#]C#读取Json数据

mikel阅读(975)

# //先在项目中添加System.Web.Extensions引用
# //using System.Web.Script.Serialization;
# JavaScriptSerializer serializer = new JavaScriptSerializer();
# Dictionary<string, object> json = (Dictionary<string, object>)serializer.DeserializeObject(
#     "{name: &#39;zswang&#39;, forum: &#39;c#&#39;}");
# object value;
# if (json.TryGetValue("name", out value))
#     Console.WriteLine(value); // 输出:zswang

[JQuery]JQuery Selectors

mikel阅读(738)

$() function

 

$(selector) 等价于 JQuery(selector),用来选取一组DOM Elements。返回的是一组预定义的JavaScript 对象,这些对象不仅封装了DOM element而且提供了许多有用的方法,以作用于这些elements。

使用CSS Selectors

 1. 可以使用的selectors如下表所示:

 

Selector               Description
*                         所有元素
E                         所有标签名(tag name)称为E的元素
E F                      所有标签名为F,且为标签E的子元素的元素(含孙子元素…)
E>F                     所有标签名为F,且为标签E直接子元素的元素
E+F                     所有标签名为F,且相邻兄弟元素标签名为E的元素
E~F                     所有标签名为F,且兄弟元素标签名为E的元素
E:has(F)               所有标签名为E, 且包含至少一个标签名为F元素的元素
E.C                      所有标签名为E, 且包含类名称为C的元素
E#I                      所有标签名为E, 且id为I的元素
E[A]                     所有标签名为E,且拥有属性名为A的元素,属性值任意
E[A=V]                 所有标签名为E,且拥有属性名为A,属性值为V的元素
E[A^=V]              所有标签名为E, 且属性名为A,属性值以V开始的元素
E[A$=V]              所有标签名为E,且属性名为A,属性值以V结尾的元素

E[A*=V]              所有标签名为E,且属性名为A,属性值包含V的元素

2. 使用position过滤器

可以使用的position过滤器包括:

 

Selector                             Description
:first                                   页面中第一个得到满足的元素. 如:li a:first 返回第一个 li 项下的链接
:last                                   页面中最后一个得到满足的元素。如:li a:last 返回最后一个 li 项下的链接
:first-child                           第一个子元素 如:li:first-child 返回 所有作为子元素的li 项中的第一li 元素
:last-child                            最后一个子元素. 如: li:last-child 返回 作为子元素的li 项中的最后一个 li 元素
:only-child                           返回所有没有兄弟元素的元素(这个元素只作为其它元素的子元素存在)
:nth-child(n)                        返回第n个子元素. 如:li:nth-child(2) 返回 所有作为子元素的 li 项的第二个.
:nth-child(even|odd)             返回偶数(Even) 或奇数(Odd) 子元素. 如:li:nth-child(even) 返回所有作为子元素的li项的偶数元素.

:nth-child(Xn+Y)                  返回Xn+Y计算结果的第n个子元素.如果Y为0,则被忽略. 如:li:nth-child(3n) 返回所有作为子元素的li项的每第3n个元素.
:even and :odd                    返回偶数(Even)或奇数(odd)个子元素。不同于nth-child系列,这个匹配所有页面中的元素(而不仅仅是作为子元素的元素).
:eq(n)                                 返回序号等于n的元素(从0基数哦)
:gt(n)                                 返回序号大于n的元素,不包括第n个元素。
:lt(n)                                  返回序号小于n的元素,不包括第n个元素。

在应用上述表时注意:所有nth-child中都是从1开始计数的,如nth-child(3n)返回第3, 6, 9个元素。其他的还是从0计数。

3. 使用JQuery自定义的过滤器

 

Selector                                    Description
:animated                                   选择那些目前在动画效果控件中的元素
:button                                      选择所有button元素(input[type=submit], input[type=reset],
input[type=button], or button).
:checkbox                                  选择checkbox元素(input[type=checkbox]).
:checked                                    选择那些被checked的checkbox或radio button(supported by CSS).
:contains(foo)                            选择包含文字foo的元素(注意区分文字的大小写哦).
:disabled                                   选择form元素中被disabled的元素(supported by CSS).
:enabled                                    选择form元素中被enabled的元素 (supported by CSS).
:file                                           选择所有file元素(input[type=file]).
:header                                     选择所有header元素; 例如:从<h1>到<h6> 的元素.
:hidden                                     选择隐藏的元素.如:$("li:hidden").css("visibility", "visible");将隐藏的li显示出来
:image                                      选择所有image元素 (input[type=image]).
:input                                       选择所有form元素(input, select, textarea, button).
:not(filter)                                 使指定filter取反.如:$("li:not(hidden)").css("visibility", "hidden");将所有没有隐藏的 li 隐藏掉
:parent                                     选择所有包含子元素的元素(including text), 空元素不算(如包含空格的).
:password                                 选择password元素(input[type=password]).
:radio                                       选择radio元素 (input[type=radio]).

:reset                                       选择reset buttons (input[type=reset] or button[type=reset]).

注意:

1) 过滤器可以连接起来使用,如:

:checkbox:checked:enabled

选择那些处于enabled状态并被选中的checkbox。

2) :not(filter) 只能用于过滤选择器(filter selectors)而不能用于查找选择器(find selectors)。如:

div p:not(:hidden)是合法的,

而 div :not(p:hidden) 就不行。

简单区分的方法是,:not只能用在以:(冒号) ,[(中括号)开始的filter selectors,其他的都不行。

 

另外,可以使用XPath Selectors,这个要使用插件,可以从这里下载。