一个很不错的加密算法,C#语言编写
算法加密特点:每次加密的结果都不同,但解密的结果都相同,而且都是加密后的数据:
Code
--加密算法:sSource是加密的字符窜
--int iFlag=1是加密 2是解密
public static string pWord(string sSource,int iFlag)
{
if(sSource==null)
return null;
if(sSource.Equals(""))
return "";
int li_len,i,li_asc,li_rand,li_head;
string ls_i,ls_code="";
if(iFlag ==1)
{
li_len=sSource.Length;
Random rdm1 = new Random(~unchecked((int)DateTime.Now.Ticks));
li_head=(int)(rdm1.NextDouble()*10);
if(li_head ==0)
li_head =1;
for(i=0; i<li_len; i++)
{
Random rdm2 = new Random(~unchecked((int)DateTime.Now.Ticks));
int rand2 =(int)(rdm2.NextDouble() *94);
if(rand2 ==0)
rand2 =1;
li_rand=rand2+32;
li_asc=Convert.ToInt32(sSource.ToCharArray(i,1)[0]);
ls_i=((char)(li_asc -i)).ToString();
if(li_asc+i+li_head>126)
{
if(li_rand%2 ==1)
li_rand=li_rand+1;
ls_i=((char)(li_rand)).ToString()+((char)(li_asc -i -li_head)).ToString();
}
else
{
if(li_rand%2 ==0)
li_rand=li_rand+1;
ls_i=((char)(li_rand)).ToString()+((char)(li_asc +i +li_head)).ToString();
}
ls_code=ls_code+ls_i;
}
Random rdm3 = new Random(~unchecked((int)DateTime.Now.Ticks));
int rand1 =(int)(rdm3.NextDouble()*9);
if(rand1 ==0)
rand1 =1;
ls_code=((char)(rand1*10+li_head+40)).ToString()+ls_code;
}
else
{
int li_ret;
li_len=sSource.Length;
ls_code="";
li_ret=Convert.ToInt32(sSource.ToCharArray(0,1)[0]) %10;
for( i=2;i <li_len; i=i+2)
{
li_asc=Convert.ToInt32(sSource.ToCharArray(i,1)[0]);
if(Convert.ToInt32(sSource.ToCharArray(i - 1,1)[0]) %2 ==0)
{
ls_i=((char)(li_asc + (i - 1)/2 + li_ret)).ToString();
}
else
{
ls_i=((char)(li_asc - (i - 1)/2 - li_ret)).ToString();
}
ls_code=ls_code+ls_i;
}
}
return ls_code;
}
对于该加密算法的使用方法:
该加密算法的特点是无论加密多少次但每次解密的结果都是一致的,有个缺点是每次无论加密和解密都需要明文,当前我们对用户登陆的用户名和密码进行加密来验证用户身份:
在Username中输入用户名(密码简化主要演示这个算法的用法),当点击加密时显示加密和解密后的数据,
第一次加密结果:
第二次加密结果:
从上面可以看出加密都是相同的数据chenkai,显示的加密结果不同,但解密的数据始终相同。
Code
--Author:chenkai Time:2009年3月3日14:33:40
--Button1点击加密的触发事件方法
protected void Button1_Click(object sender, EventArgs e)
{
//获得加密数据
string EncrytString = this.TextBox1.Text;
//进行加密
this.TextBox2.Text=pWord(EncrytString, 1);
//进行解密
this.TextBox3.Text = pWord(EncrytString, 2);
}
--从上面看出加密和解密传入的是EncrytString(chenkai),既都需要明文传入
当用户登陆时需要向服务器端传入数据和数据库进行比对,为了保证数据传输的安全性对明文数据进行该算法加密,相对而言数据库如何设计?
如果我们数据库中保存的是加密后的数据,这样的话因为每次用户登陆加密的结果都不相同,虽然保证数据安全但无法验证用户的身份。这种方案行不通
在则数据库中保存的是解密的数据,我们在用户注册时把用户登陆的用户名进行解密处理并存入数据库,根据该算法特点无论怎么加密而解密结果始终是一至的,那么用户在注册后多次登陆中对用户名进行解密并与数据库进行比对,来判断用户身份,这种方案似乎能够行得通。但这点恰恰就暴露这个算法的缺点,解密时需要明文,那么从客户端传来的是加密后的数据而非明文,这种方案也没有用 。该如何更好利用该算法呢?
我们可以这样设计数据库来利用该算法:
在数据库中存入的是明文,那么当用户登陆时有两种数据加密和解密 都是非明文,如何选择呢?上面的两种方法都选择是加密数据,死胡同一条,如果我们换一个角度换成解密数据传输到服务器端于数据库进行比对,而数据库存储的是明文对它进行解密处理,再同客户端传来的用户登陆解密数据进行比对来判断用户身份,在传输中是非明文而且还能验证客户端用户身份,这种方案能够行得通。
呵呵绕了大半天,当然这个算法设计不太好(不是很实用),但如果想用到还是有办法的。