C# 使用委托、匿名(lambda)函数和函数指针

C# 使用委托、匿名(lambda)函数和函数指针,c#,lambda,delegates,anonymous-function,C#,Lambda,Delegates,Anonymous Function,我读了一些关于匿名(lambda)函数和委托的内容。我相信我正在处理的情况是,我的职能部门中的一部分可以/应该利用它们。我不确定我的假设是否正确 当前代码: fDoSave(fGetSqlCheckEmpJob(), fGetSqlUpdateEmpJob(), fGetSqlInsertEmpJob()); fDoSave(fGetSqlCheckEmpPayrl(), fGetSqlUpdateEmpPayrl(), fGetSqlInsertEmpPayrl()); fDoSave(fGe

我读了一些关于匿名(lambda)函数和委托的内容。我相信我正在处理的情况是,我的职能部门中的一部分可以/应该利用它们。我不确定我的假设是否正确

当前代码:

fDoSave(fGetSqlCheckEmpJob(), fGetSqlUpdateEmpJob(), fGetSqlInsertEmpJob());
fDoSave(fGetSqlCheckEmpPayrl(), fGetSqlUpdateEmpPayrl(), fGetSqlInsertEmpPayrl());
fDoSave(fGetSqlCheckEEO(), fGetSqlUpdateEEO(), fGetSqlInsertEEO());
fDoSave(fGetSqlCheckEmpPhone(), fGetSqlUpdateEmpPhone(), fGetSqlInsertEmpPhone());
fGetSqlCheck…()
-将sql语句作为字符串返回,该字符串返回具有特定ID的所有行的count()
fGetSqlUpdate…()
将sql语句作为执行更新的字符串返回。
fGetSqlInsert…()
将sql语句作为执行插入操作的字符串返回。
fDoSave()

fGetSql函数如下所示:

private string fGetSql...()
{
   StringBuilder sb = new StringBuilder();
   //Create sql statement
   return sb.ToString();
}
private void fDoSave(string sSql_Check, string sSql_Update, sSql_Insert)
{
   OracleDataReader dr = ERPDB.sqlGetDataReader(sSql_Check);
   while (dr.Read())
   {
        if(fCheckIfRecrodExists(dr) > 0) //if fGetSqlCheck...() found a row with a specific ID
            //do update using sSql_Update
        else
            //do insert using sSql_Insert
    }
}
// Also often called Upsert short for "Update or Insert"
public int Save(EmpObj employeeObj) 
{
     if(CheckIfEmployeeExists(employeeObj))
     {
         return Update(employeeObj); // returns rows affected
     }
     else
     {
         return Insert(employeeObj); // Returns new Id of the employee.
     }
}

// Other methods, where the select, update and insert statements lies 
or gets called    and build
public bool CheckIfEmployeeExists(employeeObj) // Check If Employee Exists
public int Update(employeeObj); // Updates the employee
public int Insert(employeeObj); // Inserts the employee
fDoSave函数如下所示:

private string fGetSql...()
{
   StringBuilder sb = new StringBuilder();
   //Create sql statement
   return sb.ToString();
}
private void fDoSave(string sSql_Check, string sSql_Update, sSql_Insert)
{
   OracleDataReader dr = ERPDB.sqlGetDataReader(sSql_Check);
   while (dr.Read())
   {
        if(fCheckIfRecrodExists(dr) > 0) //if fGetSqlCheck...() found a row with a specific ID
            //do update using sSql_Update
        else
            //do insert using sSql_Insert
    }
}
// Also often called Upsert short for "Update or Insert"
public int Save(EmpObj employeeObj) 
{
     if(CheckIfEmployeeExists(employeeObj))
     {
         return Update(employeeObj); // returns rows affected
     }
     else
     {
         return Insert(employeeObj); // Returns new Id of the employee.
     }
}

// Other methods, where the select, update and insert statements lies 
or gets called    and build
public bool CheckIfEmployeeExists(employeeObj) // Check If Employee Exists
public int Update(employeeObj); // Updates the employee
public int Insert(employeeObj); // Inserts the employee

是否可以使用lambda函数或委托重新编写,是否应该这样做?应该怎么写呢?

你的问题仍然很模糊,但我会这样说

案例:

1:可重复使用和“静态”
如果重用SQL语句并且它们有些静态,请将它们放在属性中。考虑更好的名字。

2:虽然简单,但可重复使用但“可变”
如果重用SQL语句,并且它们是可变的,但不占用太多CPU,这意味着它们会因不同的状态而变化,并且创建和构建速度非常快,那么就让它们保持原样吧

3:可重复使用但“可变”且复杂
如果重用SQL语句,并且它们是可变的,但非常复杂,需要大量CPU资源,请将它们放在方法中,但作为委托调用它们,不要使它们匿名

4:不可重复使用,但“可变”且复杂 如果您永远不会重用SQL语句(这种情况可能永远不会发生),并且它们是可变的、非常复杂的,并且需要大量的CPU资源,请将它们放在一个匿名函数中

在所有情况下
使用更好的名字

我的建议
我更喜欢案例1和案例2,因为其余的似乎是一个可能不存在的问题的过于复杂的解决方案。
另外,我不知道您的整个代码库,但我不喜欢应该保存的对象没有提供给fDoSave()

我会这样做:

private string fGetSql...()
{
   StringBuilder sb = new StringBuilder();
   //Create sql statement
   return sb.ToString();
}
private void fDoSave(string sSql_Check, string sSql_Update, sSql_Insert)
{
   OracleDataReader dr = ERPDB.sqlGetDataReader(sSql_Check);
   while (dr.Read())
   {
        if(fCheckIfRecrodExists(dr) > 0) //if fGetSqlCheck...() found a row with a specific ID
            //do update using sSql_Update
        else
            //do insert using sSql_Insert
    }
}
// Also often called Upsert short for "Update or Insert"
public int Save(EmpObj employeeObj) 
{
     if(CheckIfEmployeeExists(employeeObj))
     {
         return Update(employeeObj); // returns rows affected
     }
     else
     {
         return Insert(employeeObj); // Returns new Id of the employee.
     }
}

// Other methods, where the select, update and insert statements lies 
or gets called    and build
public bool CheckIfEmployeeExists(employeeObj) // Check If Employee Exists
public int Update(employeeObj); // Updates the employee
public int Insert(employeeObj); // Inserts the employee

所有这些方法都是什么?如果你否决了一个问题,那么解释为什么以及如何改变这个问题将是一种常见的礼貌(也是非常有帮助的)。我不能,因为你的问题对我来说没有任何意义。我们需要看看每种方法的作用,做出任何判断。因为代码并不是很清楚它是做什么的。此外,你可以考虑改变你的编码风格,如果这是你的代码。@ I4V,“这能用lambda函数或代表重写吗?它应该是什么?它应该如何被重写?”你觉得有挑战性的理解吗?我感谢你花时间回答并提出建设性的意见。关于命名约定。我的公司有一个命名惯例,我必须遵守。另外,我认为fGetSqlInsertEmpPayrl非常具有描述性对于函数“GetSql”,它将返回一个sql语句“Insert”,因为它将是一个Insert语句“EmpPayrl”,因为它是在该表上运行的。请让我知道什么是更好的/你的方法。在你更新你的答案后,我理解你不喜欢代码的地方。我不能这样做,因为它不是我的代码,它是一个庞大而古老的代码库的一部分。项目要求的一部分是尽量减少代码更改。:)你回答的第二部分是一个很好的建议,但与我的问题无关。我没有问“如何重新编写我的代码,就像它不是1996年一样”:(首先,我不喜欢匈牙利风格,但这比什么都重要,除了GetSql。。。看起来像java getter,这可能表明您没有充分利用C。最后,我不完全确定你的代码做了什么,以及它为什么这样做。fDoSave,为什么需要3条SQL语句?直到你进一步解释,我才知道,但这是一个结构性问题,而不是命名约定问题。@Azzi当然,我有点期待你的回答,这也是为什么它只是一个建议,与你最初的问题没有实际的背景。@Azzi很好,我想是的,你仍然可以选择属性,但在类别1和类别2中,您可以为不同的场景选择您想要的,但是通过对变量语句使用方法而不是属性(可以解决相同的问题),方法告诉未来的开发人员,这是一个比预设值更复杂的过程。-我也很高兴能帮上忙:)