2

私はプログラミングの初心者ですが、以前の従業員が作成したいくつかのアプリケーションの保守を任されています。true または false ステートメント以上のものを処理する必要がある ?: ステートメントがありますが、それを行う方法がわかりません。問題のコードは次のとおりです。

    MailDomainContext mail = new MailDomainContext();
      mail.Load(mail.GetMailsQuery("Workforce Attendence Issue",
               loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().Username,
               (loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().EmployeeShiftID >= 2 ? "supervisor1" : "supervisor2"),
               loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().FirstName,
               attendence.AttendenceDate.ToString("MM/dd/yyyy"),
               attendence.TimeLost,
               loadAbs.Entities.Where(abs => abs.AbsenceID == attendence.AbsenceID).First().AbsenceDescription,
               (from inf in loadAtt.Entities
               where inf.EmployeeID == _EmployeeID
               where inf.AttendenceDate > DateTime.Now.AddDays(30 * -1)
               where inf.Approved == false
               select inf).Count() + 1,
               attendence.UTOUsed
               ), null, null);

より具体的には、この行:

    (loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().EmployeeShiftID >= 2 ? "supervisor1" : "supervisor2"),

リストにさらに4人の監督者を追加する必要がありますが、他のすべてを不幸にしない方法がわかりません. これがあまりにも単純な質問だったり、知っておく必要があるかもしれない詳細を省略したりした場合は、申し訳ありません。私はこれらすべてにかなり慣れていないと言いました。

4

5 に答える 5

4

このコードは維持するのが不必要に難しく、非効率的で防御的でもありません。コードは従業員を 3 回取得しています。

loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().Username

_EmployeeID従業員が存在しない場合、上記の行 (およびその他) は例外をスローします。代わりにFirstOrDefault、またはSingleOrDefaultその ID を持つ従業員が 1 人しかいないと予想される場合 (そのエンティティの主キーのように見えるので、そうなるはずです) を使用できます。loadEmpが実際に Entity Framework である場合は、DbContextも使用できますFind

このクエリを 1 回実行して、結果をローカル変数に格納できます。

var employee = loadEmp.Entities.SingleOrDefault(emp => emp.EmployeeID == _EmployeeID);

if (employee == null)
{
   // Handle employee not found
}

次に、従業員に基づいてスーパーバイザー文字列を取得するには、スーパーバイザー文字列を計算するために必要な最小限の情報を取得するメソッドを作成し、これをメソッドに渡して結果を取得します。

GetSupervisorRole(employee.EmployeeShiftID);

...

private string GetSupervisorRole(int employeeShiftID)
{
   // Logic here
}
于 2012-08-31T19:41:56.800 に答える
3

1 つのアプローチは、そのコードをメソッドに抽出し、そのメソッドを好きなように記述することです。

別のアプローチは、ディクショナリを使用してキー (キーの数が少ない場合) を値にマップすることです。

var id =3;
var mapping = new Dictionary<int, string>() { 
  { 1, "first" },
  { 2, "second" },
  { 3, "first" } //you can map 2 values (1,3) to the same "first" string
};

string value;
if (!mapping.TryGetValue(id, out value))
{
  value = "unknown";
}
于 2012-08-31T19:38:27.250 に答える
2

次のメソッドを作成します。

string GetSupervisor(int employeeShiftId) {
    if (employeeShiftId == 1) supervisor = "supervisor1";
    else if (employeeShiftId == 2) supervisor = "supervisor2";
    else if (employeeShiftId == 3) supervisor = "supervisor3";
    else if (employeeShiftId == 4) supervisor = "supervisor4";
}

次に、コードから呼び出して、結果を変数に割り当てますsupervisor。これを で使用できますmail.Load()

int employeeShiftId = loadEmp.Entities
          .Where(emp => emp.EmployeeID == _EmployeeID).First()
          .EmployeeShiftID;
string supervisor = GetSupervisor(employeeShiftId);

MailDomainContext mail = new MailDomainContext();
mail.Load(mail.GetMailsQuery("Workforce Attendence Issue",
               loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().Username,
               supervisor, // <-- Then use it here
               ...
);
于 2012-08-31T19:43:01.797 に答える
2

このセクション全体を置き換えます

loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().Username,
(loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().EmployeeShiftID >= 2 ? "supervisor1" : "supervisor2"),
 loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First().FirstName,

//Assign these variables ahead of time so others reading your code can 
//figure out what's going on
var EmpID = loadEmp.Entities.Where(emp => emp.EmployeeID == _EmployeeID).First();
var UserName = EmpID.UserName;
var FirstName = EmpID.FirstName;
var Title = GetTitle(EmpID.EmployeeShiftID);

//Your original call
Mail.Load(mail.GetMailsQuery("Workforce Attendence Issue",
     UserName,
     Title,
     FirstName,
     //...Etc
);

//New method you will need to add, you could do this logic in line, but this will
//be less messy
private string GetTitle(int ShiftID)
{
    switch (ShiftID)
    {
         case 1:
             return "supervisor1";
             break;
         case 2:
             return "supervisor2";
             break;
         //...etc
    }
}
于 2012-08-31T19:45:11.030 に答える
1

これは素晴らしいアイデアではありませんが、インラインの if を次のように組み合わせることができます。

    static void Main(string[] args)
    {
        int EmpId = 2;
        string supervisor = EmpId == 4 ? "Supervisor4" :
                            EmpId == 3 ? "Supervisor3" :
                            EmpId == 2 ? "supervisor2" :
                                         "supervisor1" ;
        Console.WriteLine(supervisor);

    }

別のスタックの質問でこの別の例を見ることができます:判読可能かどうか: C# 複数の 3 項演算子 + 一致しない場合はスロー

代わりに、EmpId を渡してスーパーバイザー名を取得するだけで KDiTraglia が提案したメソッド アプローチ、または代わりに Alexei Levenkov が提案したようなディクショナリ ルックアップ アプローチを使用することになるでしょう。

于 2012-08-31T19:38:16.050 に答える