2012-07-03 88 views
1

我有一個datagridview,我想根據從用戶輸入的字符串部分對行進行排序。輸入的字符串與特定列中的所有字符串進行比較。例如,如果我給「comp」作爲搜索詞,程序會嘗試將搜索詞與第一列的字符串進行比較,並按照「comp」開頭的降序對行進行排序,如「compare」, 「組成」,「計算機」等。其餘不匹配的單詞要麼單獨存在,要麼按字母順序排序(以較容易的爲準)。基於匹配字符串的Datagridview排序列

在LINQ,我知道,你可以將下面的代碼來實現你想要一個字符串數組什麼:

var sortedWords = words.Where(x => x.Contains("comp")) 
         .OrderByDescending(x => x); 

我怎樣才能實現的DataGridView同樣的事情,我需要的行排序,而不僅僅是特定列內的項目?

編輯:

以下代碼給出了一個System.InvalidOperationException。 (SetCurrentCellAddressCore被稱爲兩次)

private void DGVPointCtrl_CellEndEdit(object sender, DataGridViewCellEventArgs e) 
    { 
     MatchComparer mc = new MatchComparer(); 
     DGVPointCtrl.Sort(mc); //Error 
    } 

我可能做錯了什麼,但我不知道爲什麼。下面是編程的行添加用於測試目的的代碼:

private void BtnRefresh_Click(object sender, EventArgs e) 
     { 
      try 
      { 
       DGVPointCtrl.Rows.Clear(); 
       int mainIndex = CmbMainDevice.SelectedIndex; 
       int subIndex = CmbSubDevice.SelectedIndex; 
       DDCDAO ddcdao = new DDCDAO(DDCGlobal.ddcEngineIP, ddc.Ip); 
       string pointListType; 
       object rs; 

       //Currently only supports IO DDC Request 
       //TO DO: Change DDCDAO to send proper subdevice requests 

       if (mainIndex == 0) //IO 
       { 
        #region Main Device: IO 
       } 


       //First row is for searching items 
       DGVPointCtrl.Rows.Add(new DataGridViewRow()); 
       for (int i = 1; i < 5; i++) 
       { 
        DGVPointCtrl.Rows.Add(new DataGridViewRow()); 
        DGVPointCtrl.Rows[i].ReadOnly = true; 
       } 
       DGVPointCtrl.Columns[0].SortMode = DataGridViewColumnSortMode.Programmatic; 
       DGVPointCtrl.Rows[0].DefaultCellStyle.Font = 
       new Font(DGVPointCtrl.DefaultCellStyle.Font, FontStyle.Italic | FontStyle.Bold); 

       if (subIndex == 1) //BI 
       { 
        PointDGVColumnGenerate("IO_BI"); 

       } 
       else if (subIndex == 2) //BO 
       { 
        PointDGVColumnGenerate("IO_BO"); 
       } 
       else if (subIndex == 3) //AI 
       { 
        PointDGVColumnGenerate("IO_AI"); 
       } 
       else if (subIndex == 4) //AO 
       { 
        PointDGVColumnGenerate("IO_AO"); 
       } 

       DGVPointCtrl.Rows[1].Cells[0].Value = "IO12314"; 
       DGVPointCtrl.Rows[2].Cells[0].Value = "IO21948"; 
       DGVPointCtrl.Rows[3].Cells[0].Value = "IO28194"; 
       DGVPointCtrl.Rows[4].Cells[0].Value = "VP12984"; 
       DGVPointCtrl.Rows[2].Cells[1].Value = "asdf"; 

       #endregion 
      } 
      catch 
      { 
      } 
     } 

    private void PointDGVColumnGenerate(string key) 
    { 
     int colCount = 0; 
     DGVColumnTable.Clear(); 

     for (int i = 0; i < COL_MAX; i++) 
     { 
      DGVPointCtrl.Columns[i].HeaderText = " "; 
      DGVPointCtrl.Columns[i].Visible = true; 
     } 

     foreach (string s in UIConstant.DDCPCtrlListColumnText[key]) 
     { 
      DGVPointCtrl.Columns[colCount].HeaderText = s; 
      DGVColumnTable.Add(DGVPointCtrl.Columns[colCount]); 
      colCount++; 
     } 
    } 

EDIT2:

public class MatchComparer : IComparer 
{ 
    private static IComparer defaultComparer = new CaseInsensitiveComparer(); 
    int IComparer.Compare(object x, object y) 
    { 
     DataGridViewRow xr = (DataGridViewRow)x; 
     DataGridViewRow yr = (DataGridViewRow)y; 

     string xs = ""; 
     string ys = ""; 
     try 
     { 
      xs = xr.Cells[0].Value.ToString(); 
     } 
     catch 
     { 
     } 
     try 
     { 
      ys = yr.Cells[0].Value.ToString(); 
     } 
     catch 
     { 
     } 

     if (HasMatch(xs) && !HasMatch(ys)) return -1; 
     else if (!HasMatch(xs) && HasMatch(ys)) return 1; 
     else return defaultComparer.Compare(xs, ys); 
    } 

回答

1

這是可能的,只有你自己填充網格,而不是將其綁定到數據庫。

設置DataGridViewColumn.SortModeProgrammatic

使用DataGridView.Sort強加一個比較器是這樣的:

public class MatchComparer : IComparer { 
    int IComparer.Compare(object x, object y) { 
     if (HasMatch(x) && !HasMatch(y)) return -1; 
     else if (!HasMatch(x) && HasMatch(y)) return 1; 
     else return defaultComparer.Compare(x, y); 
    } 

    private bool HasMatch(object x) { 
     return x is string && ((string)x).StartsWith("comp"); 
    } 

    private static IComparer defaultComparer = new CaseInsensitiveComparer(); 
} 
+0

的代碼有一些編譯器錯誤..其實很多錯誤。 IComparer需要指定類型,defaultComparer.compare不會將對象作爲參數,defaultComparer不能指定CaseInsensitiveComparer。 – l46kok

+0

沒關係,只要我包含集合命名空間,它就會工作! – l46kok

+0

@SokwhanHuh - 就是這樣。我剛編輯相距數錯別字,最重要的調用'defaultComparer'當交換參數。 –

相關問題