集合

2014-10-03 39 views
0

我有Setting对象具有以下结构的列表中搜索特定字符串的令牌:集合

public class Setting 
{ 
     int SettingID; 
     string UserIDList; 
} 

UserIDList属性存储用户ID列表作为逗号分隔值,例如“32,45,22,53”,其中用户ID可以存在于多个对象中。现在假设我想搜索包含特定用户ID(例如“45”)的任何对象的整个集合,那么执行此操作的最有效方法是什么?

我简要地考虑遍历列表,分裂UserIDList,然后做比较,在那里,但是这似乎没有效率的我。我觉得可能有更好的方法来做到这一点。 不幸的是,改变对象的结构不存在问题。你怎么看?

+2

在哪种情况下高效/低效?桌面计算机上有1000个项目,用户从UI中触发一次操作,其中数据来自非本地数据库?写什么更可读的(见解答)和容易... – 2014-10-03 13:01:18

+0

我建议改变'Setting'到'UserIDList'存储为'名单'如果可能的话。 – juharr 2014-10-03 13:01:37

+1

用户正则表达式 – RAJ 2014-10-03 13:03:05

回答

0

你可以使用LINQ做到这一点:

var result = from setting in settingList 
      where setting.UserIdList.Split(',').Contains("45") 
      select setting; 
+0

“Contains”方法作用于列表而不是字符串。 List.Contains(“45”)测试列表中的某个元素是否等于“45”。因此,如果字符串包含“457”,则不会被采用。 – Thibaut91170 2014-10-03 13:29:29

0
settingList.Where(s => s.UserIDList == "45" || 
         s.UserIDList.StartsWith("45,") || //LIKE('45,%') 
         s.UserIDList.EndsWith(",45") || //LIKE('%,45') 
         s.UserIDList.Contains(",45,")) //LIKE('%,45,%') 
1

您可以用正则表达式做到这一点。

List<Setting> FindItemsInList(List<Setting> settings, string val) 
{ 
    var result = new List<Setting>(); 
    var searchRegEx = new RegEx(@"\b" + val + @"\b"); 
    foreach (var s in settings) 
    { 
     if (searchRegEx.IsMatch(s.UserIDList)) 
     { 
      result.Add(s); 
     } 
    } 
    return result; 
} 

的这里的想法是,在正则表达式使用\b元字符只能获得整个单词。创建的正则表达式的格式为“”\ b45 \ b“。

这样可以正确处理值位于字符串开头,字符串末尾以及中间任何位置的情况,并且不会错误地告诉您“457”匹配“45”。

可以缩短与LINQ。将环路替换为:

var result = settings.Where(s => searchRegEx.IsMatch(s.UserIDList)).ToList();