处理 (2 raise to n) -1 条件

发布于 2024-10-01 15:58:27 字数 756 浏览 3 评论 0原文

我有一个逻辑问题。我有员工对象的集合 有3个过滤条件,有句柄 例如员工姓名、办公室名称、工资。

现在这些过滤条件应该匹配(员工姓名和/或办公室名称和/或薪水),

所以在这里我必须编写 (2 raise n) -1 if 条件来处理这种情况。

我们还有其他方法可以做到这一点吗? 对于(员工姓名和/或办公室名称)条件,我正在执行以下操作

if (criteria.EmpName != "" && criteria.OfficeName != "")
    {  
      if (emp.EmpName == criteria.EmpName && emp.OfficeName == criteria.OfficeName) 
        {
              bIsMatch = true;
         }
    }
    else
    {
          if (criteria.EmpName != "" && emp.EmpName == criteria.EmpName)
             bIsMatch = true;
          else if (criteria.OfficeName != "" && emp.OfficeName == criteria.OfficeName)
            bIsMatch = true;
    }

,现在如果必须处理萨拉利,我也写了至少 5 个条件。

还有其他方法吗?

I have one logical question. I have collection of employee objects
There are 3 filter criteria conditions which have handle
For e.g. Employee name, Office name, salary.

Now these filter criteria should match like (Employee name AND/OR Office name AND/OR salary)

So here I have to write (2 raise n) -1 if conditions to handle this situation.

Is there any other way we can do this.
For (Employee name AND/OR Office name) condition I m doing following

if (criteria.EmpName != "" && criteria.OfficeName != "")
    {  
      if (emp.EmpName == criteria.EmpName && emp.OfficeName == criteria.OfficeName) 
        {
              bIsMatch = true;
         }
    }
    else
    {
          if (criteria.EmpName != "" && emp.EmpName == criteria.EmpName)
             bIsMatch = true;
          else if (criteria.OfficeName != "" && emp.OfficeName == criteria.OfficeName)
            bIsMatch = true;
    }

Now if have to handle saraly also i have write min 5 conditions.

Is thr other way to do it?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

迷途知返 2024-10-08 15:58:27

有很多方法可以做到这一点,但是由于您没有指定一种特定语言,并且我觉得没有资格判断您的编码风格,因此这里有一种保留代码的一般形式,同时演示一些更好的逻辑的方法:

bool bIsMatch = true;
if (criteria.EmpName != "" && criteria.EmpName != emp.EmpName) {
    bIsMatch = false;
} else if (criteria.OfficeName != "" && criteria.OffIceName != emp.OfficeName) {
    bIsMatch = false;
} /* Repeat for as many conditions as there are */

if (bIsMatch) {
    /* None of the checks above failed */
}

There are lots of ways to do it, but since you didn't specify one specific language and since I don't feel qualified to judge your coding style, here's one that keeps the general form of your code, while demonstrating some better logic:

bool bIsMatch = true;
if (criteria.EmpName != "" && criteria.EmpName != emp.EmpName) {
    bIsMatch = false;
} else if (criteria.OfficeName != "" && criteria.OffIceName != emp.OfficeName) {
    bIsMatch = false;
} /* Repeat for as many conditions as there are */

if (bIsMatch) {
    /* None of the checks above failed */
}
如此安好 2024-10-08 15:58:27

您可以配对过滤条件并使用一个语句对所有参数进行编码:

if( (criteria.EmpName.equals("") || criteria.EmpName.equals(emp.EmpName))
    && (criteria.OfficeName.equals("") || criteria.OfficeName.equals(emp.OfficeName))
    && (criteria.Salary.equals("") || criteria.Salary.equals(emp.Salary)))

在每个 AND 表达式中,首先检查过滤器是否为空,如果是,则该部分将返回 true ,如果不是,则针对 emp 中的相应值执行检查,并且仅当该检查为 true 时才为 true

You can pair up your filtering conditions and have a single statement that encodes all the parameters:

if( (criteria.EmpName.equals("") || criteria.EmpName.equals(emp.EmpName))
    && (criteria.OfficeName.equals("") || criteria.OfficeName.equals(emp.OfficeName))
    && (criteria.Salary.equals("") || criteria.Salary.equals(emp.Salary)))

In each of the AND-ed expressions checks first if the filter is empty, if it is that piece will result in true, if it's not, then the check is performed against the corresponding value in emp and is true only when that check is true.

逆光下的微笑 2024-10-08 15:58:27

首先假设您有一场比赛,然后一一应用每个标准。

bIsMatch = true;

if (bIsMatch && criteria.EmpName    != "") bIsMatch = emp.EmpName    == criteria.EmpName;
if (bIsMatch && criteria.OfficeName != "") bIsMatch = emp.OfficeName == criteria.OfficeName;
// ...

或者,编写一个执行匹配的辅助函数。

bool IsMatch(String criterion, String value)
{
    return criterion == "" || criterion == value;
}

然后你可以在一个大的 if 语句中完成所有操作:

if (IsMatch(criteria.EmpName,    emp.EmpName)    &&
    IsMatch(criteria.OfficeName, emp.OfficeName) &&
    ...
   )

Start out by assuming you have a match and Then apply each criterion one by one.

bIsMatch = true;

if (bIsMatch && criteria.EmpName    != "") bIsMatch = emp.EmpName    == criteria.EmpName;
if (bIsMatch && criteria.OfficeName != "") bIsMatch = emp.OfficeName == criteria.OfficeName;
// ...

Or, write a helper function that does the matching.

bool IsMatch(String criterion, String value)
{
    return criterion == "" || criterion == value;
}

Then you can do everything in one big if statement:

if (IsMatch(criteria.EmpName,    emp.EmpName)    &&
    IsMatch(criteria.OfficeName, emp.OfficeName) &&
    ...
   )
羞稚 2024-10-08 15:58:27

您可以单独检查条件并维护匹配的计数。这样你只需要 n 个条件:

int matches = 0;

if (criteria.EmpName != "" && emp.EmpName == criteria.EmpName)
  matches++;
// similar code for other criteria

if (matches >= 2) { // as many matches as required
  // succeeded
}

You can check the criteria individually and maintain a count of matches. That way you need only n conditions:

int matches = 0;

if (criteria.EmpName != "" && emp.EmpName == criteria.EmpName)
  matches++;
// similar code for other criteria

if (matches >= 2) { // as many matches as required
  // succeeded
}
初心未许 2024-10-08 15:58:27

这个怎么样?这个想法可以很好地适应更多的过滤器,除了映射本身是基于约定的(名称 - 名称)。

var map = new Dictionary<string, string>
              {
                { criteria.EmpName, emp.EmpName },       
                { criteria.OfficeName, emp.OfficeName},
                { criteria.ThirdProp, emp.ThirdProp }
              };

bIsMatch = dict.All(kvp => string.IsNullOrEmpty(kvp.Key) || kvp.Key == kvp.Value);

不过,我会对整体设计提出质疑;事情似乎有些不对劲。您将如何处理您提到的 Salary 字段?当然,这不是一个字符串?在这种情况下使用的哨兵值是什么?

How about this? The idea scales well for more filters, except that the mapping itself is convention based (name - name).

var map = new Dictionary<string, string>
              {
                { criteria.EmpName, emp.EmpName },       
                { criteria.OfficeName, emp.OfficeName},
                { criteria.ThirdProp, emp.ThirdProp }
              };

bIsMatch = dict.All(kvp => string.IsNullOrEmpty(kvp.Key) || kvp.Key == kvp.Value);

I would question the overall design though; there's something that doesn't seem right about it. How would you deal with the Salary field that you mention? Surely, that's not a string? What's the sentinel-value being used in that case?

凹づ凸ル 2024-10-08 15:58:27

在编写代码之前,请确保您对业务逻辑足够清晰。根据您的代码,我可以看到您想要检查 empcriteria 是否具有相同的 EmployeeNameOfficeName >,如果任何属性是 string.Empty,则被认为是相同的。自己清楚之后代码就相当清晰了。开始了:

public static bool EmptyOrEquals(this string one, string another)
{
    return string.IsNullOrEmpty(another) || one.Equals(another);
}
bIsMatch = emp.EmpName.EmptyOrEquals(criteria.EmpName) 
            && emp.OfficeName.EmptyOrEquals(criteria.OfficeName);

Make sure you are clear enough about the business logic before writing the code. According to your code, I can see that you want to check if emp and criteria have the same EmployeeName and OfficeName, any of the properties is considered to be the same if it's string.Empty. The code will be quite clear after yourself is clear. Here we go:

public static bool EmptyOrEquals(this string one, string another)
{
    return string.IsNullOrEmpty(another) || one.Equals(another);
}
bIsMatch = emp.EmpName.EmptyOrEquals(criteria.EmpName) 
            && emp.OfficeName.EmptyOrEquals(criteria.OfficeName);
帥小哥 2024-10-08 15:58:27

单独测试每个问题并使用位集对答案组合进行编码。

这会产生更干净的代码,因为您只需测试每个条件一次,它紧凑且可读,而且您可以轻松插入代码来处理每个组合。而且速度也很快。 O(n) 测试所有标准,O(1) 找到实际组合。

对于少量固定数量的条件,您可以手动推送位。对于许多标准或可扩展的解决方案,请使用 java.util.BitSet

位推送示例:

int bits = 0;

if (...criteria 1...) {
    bits = 1;
}

if (...criteria 2...) {
    bits |= 2;
}

if (...bits 3...) {
    bits |= 4;
}

switch (bits) {
case 0: // no criteria matched
    ;
case 1: // criteria 1 matched
    ;
case 2: // criteria 2 matched
    ;
case 3: // criteria 1 AND 2 matched
    ;
case 4: // criteria 3 matched
    ;
case 5: // criteria 1 AND 3 matched
    ;
case 6: // criteria 2 AND 3 matched
    ;
case 7: // criteria 1 AND 2 AND 3 matched
    ;
} 

您可以使用 java.util.BitSet 来概括此解决方案以操作 n 个标准的位(当 n > 64 时有用!)。为了便于快速查找,请将每个 BitSet 组合的哈希存储在将哈希代码映射到命令类的映射中。

Test each question individually and use a bit set to encode the combinations of answers.

This results in cleaner code because you only test each criteria once, it's compact yet readable, and yet you can easily plug in code to handle each combination. And it's the fast too. O(n) to test all the criteria and O(1) to find the actual combination.

For a small, fixed number of criteria, you can push bits around manually. For many criteria, or for a solution that scales, use java.util.BitSet

Bit pushing example:

int bits = 0;

if (...criteria 1...) {
    bits = 1;
}

if (...criteria 2...) {
    bits |= 2;
}

if (...bits 3...) {
    bits |= 4;
}

switch (bits) {
case 0: // no criteria matched
    ;
case 1: // criteria 1 matched
    ;
case 2: // criteria 2 matched
    ;
case 3: // criteria 1 AND 2 matched
    ;
case 4: // criteria 3 matched
    ;
case 5: // criteria 1 AND 3 matched
    ;
case 6: // criteria 2 AND 3 matched
    ;
case 7: // criteria 1 AND 2 AND 3 matched
    ;
} 

You can generalize this solution using java.util.BitSet to manipulate bits for n criteria (useful when n > 64!). To facilitate quick look up, store the hash of each BitSet combination in a map that maps the hash code to a command class.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文