2012-12-18 32 views
1

下面是一个名为Password_Click的按钮事件处理程序。当你点击这个按钮时,它会进入数据库并找到一个名为TblMaintenance的表。一旦进入表中,它将查找表中字段Patrol = True或1的所有记录,并使用系统生成的随机4位数字更新字段Password(也在表中)。用随机数字更新多行

我的问题是每一行都会使用相同的随机后卫密码进行更新。我希望每行有一个不同的随机4位数字。在一分钟它这样做,我不希望它做的:

站点密码巡逻 CEP 5405 1 GNK 5405 1 ILT 5405 1 KHA 5405 1

但我想它这样做而不是:

站点密码巡逻 CEP 4567 1 GNK 9000 1 ILT 4345 1 KHA 1278 1

protected void lnkPassword_Click(object sender, EventArgs e) 
{ 
    var random = new Random(); 
    var i = random.Next(1000, 9999); 

    SqlHelper.ExecuteSqlNonQuery(@"update Tblmaintenance set 
            GuardPassword = @newPassword 
            WHERE Patrol = 1", 
            "newPassword", i);       
} 
+0

你必须记得在你完成测试后给你的随机数发生器播种 –

+1

由于你正在生成密码,你应该使用一个密码强的随机生成器,而不是'Random'。 – Servy

回答

0

问题是你的SQL语句。它正在更新ManagedGuardPatrol值等于1的所有记录。每次调用click事件时,它们都将具有相同的GuardPassword值。您需要使用YardCode来标识要更新的记录。

为了澄清,随机数在C#中生成并传递给SQL语句一次。这个相同的值通过所有匹配的行传播。

i = 4505; // a number that was randomly generated ONCE. 

你的SQL语句变成:

update T2_SecurityKeyHolder 
set GuardPassword = 4501 
WHERE ManagedGuardPatrol = 1 

哪些更新与一个随机值都匹配的记录。

如果我能想出一个更清晰的方式来解释它,我会的。目前,足以说,你只能生成一个具有固定值的SQL语句。

+0

可否请给我写一个例子来帮助我理解请。如果你不介意请 – john

1

如果您在Visual Studio中使用DataContext(dbml),则可以使用LINQ而不是SQL来回记录并使用C#代码编辑它们。

DatabaseDataContext db = new DatabaseDataContext(); 

foreach(T2_keyHolderMaintenance t2 in (from t2 in db.T2_keyHolderMaintenances where t2.ManageGuardPatrol == true select t2).ToList()) 
{ 
    t2.GuardPassword = Math.Random() //or whatever you want to do 
} 

db.SubmitChanges(); 
+0

为什么'ToList'?没有必要急切地评估整个查询到一个单独的数据结构来对其进行处理。 – Servy

+0

非常感谢James的回复 – john

1

您的问题一点点的解决方法可能是:

protected void lnkUpdateGuardPassword_Click(object sender, EventArgs e) 
{ 
    //command = query to select all the yard codes. 

    List<string> YardCodes = new List<string>(); 
    SqlDataReader reader = command.ExecuteReader(); 
    while (reader.Read()) 
    { 
     YardCodes.Add(reader["YardCode"].ToString()); 
    } 

    var random = new Random(); 
    foreach (var yardcode in YardCodes) 
    { 
     var i = random.Next(1000, 9999); 
     SqlHelper.ExecuteSqlNonQuery(@"update T2_SecurityKeyHolder set 
           GuardPassword = @newPassword 
           WHERE YardCode = @yardcode", 
           "newPassword", yardcode, i); 
    }      
} 

这将首先获得所有yardcodes(假定它们是唯一的),然后设置一个随机为每个yardcode。

+0

如果您有很多条目,这并不能很好地扩展,您可能需要对响应进行批处理以减少网络流量。对于较小的数据集,这是很好的。 – Servy

+0

感谢您的回复,最有帮助!你们是伟大的 – john

0
protected void lnkPassword_Click(object sender, EventArgs e) 
{ 
    SqlHelper.ExecuteSqlNonQuery(@"update Tblsecurity set 
            Password = abs(checksum(NewId())) % 10000 
            WHERE Patrol = 1");       
} 

protected void lnkUpdateGuardPassword_Click(object sender, EventArgs e) 
{ 
    SqlHelper.ExecuteSqlNonQuery(@"update Tblsecurity set 
            Password = ROUND(((9999 - 1000 -1) * RAND() + 1000), 0) 
            WHERE Patrol = 1");       
} 
2

如果你想与您可以使用下面的一个DML语句留着,

update tbl_Security set 
          GuardPassword = round(rand(CAST(CAST(NEWID() AS VARBINARY(4)) AS SMALLINT))* 9000,0) + 1000 
          WHERE Patrol = 1 

应该产生的每一行新的四指数遵守where语句。

+0

这很棒。你的方法完美运作。非常感谢你。你介意给我解释代码的含义吗?我在 – john

+0

之前没有使用过这种说法。 NewID() - 生成唯一标识符 - 然后我将其转换为VARBINARY,然后转换为INT。 Rand() - 生成0到1之间的随机数(带浮点数)。 我乘以9000的原因是因为我需要得到浮点数 - 0.xxxxxxxx - 形式为xxxx.xxxxxxx。它应该是10000,但我已经将它更改为9000,并添加了1000,以确保结果编号在1000和9999之间。 希望能帮到:) –