首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >检查移动模拟人生

检查移动模拟人生
EN

Code Review用户
提问于 2012-10-28 07:57:36
回答 3查看 204关注 0票数 2

有人能改进这段代码吗?我需要消除for循环。

代码语言:javascript
运行
复制
public bool CheckMobileSim(List<Mobile_Range> numberRange, string MobileNumber)
{
    bool SimType = new bool();
    string NineDigits = MobileNumber.Substring(0, 9).ToString();
    long Number = Convert.ToInt64(NineDigits);
    if (numberRange != null)
    {
        if (numberRange.Count > 0)
        {
            for (int i = 0; i < numberRange.Count; i++)
            {
                if ((Number >= numberRange[i].RangeStart && Number < numberRange[i].RangeEnd))
                {
                    SimType = true;
                    break;
                }

            }
        }
    }

    return SimType;
}
EN

回答 3

Code Review用户

发布于 2012-10-28 15:20:59

重构步骤1,删除不必要的变量和大括号,并提前返回。

代码语言:javascript
运行
复制
public bool CheckMobileSim(List<Mobile_Range> numberRange, string MobileNumber)
{
    if(numberRange == null)
        return;
    string NineDigits = MobileNumber.Substring(0, 9).ToString();
    long Number = Convert.ToInt64(NineDigits);
    for (int i = 0; i < numberRange.Count; i++)
        if ((Number >= numberRange[i].RangeStart && Number < numberRange[i].RangeEnd))
            return true;

    return false;
}

我意识到这与“单点回报”的智慧不同,但我并不是一个超级粉丝。当你有像这样的小函数时,这就没有什么意义了。

重构步骤2,经过清理,很容易看出这如何适合于一个简单的LINQ查询

代码语言:javascript
运行
复制
public bool CheckMobileSim(IEnumerable<Mobile_Range> numberRange, string mobileNumber)
{
    if(numberRange == null || String.IsNullOrWhitespace(mobleNumber))
        return false;

    var nineDigits = mobileNumber.Substring(0, 9);
    var number = Convert.ToInt64(nineDigits);

    return numberRange.Any(n => number >= n.RangeStart && number < n.RangeEnd);
}

由于这是一种公共方法,所以我在IEnumerable中添加了一些检查和下拉列表,这是一个更宽松的契约,您在这里真正需要的就是这个。

顺便说一下,.Net命名约定是用于私有变量的pascalCase和用于公共和保护的局部变量CamelCase。很少使用下划线。

票数 1
EN

Code Review用户

发布于 2012-10-29 08:55:29

你可以这样改进它:

(在代码下面,我谈到了我为什么要做更改)

代码语言:javascript
运行
复制
public bool CheckMobileSim(IEnumerable<MobileRange> numberRange, string mobileNumber)
{
    // Sanity checks: You can return false instead of throwing exceptions if you'd like to.
    if (numberRange == null)
        throw new ArgumentNullException("numberRange");

    if (mobileNumber == null)
        throw new ArgumentNullException("mobileNumber");

    // More sanity checks: You need to be sure that mobileNumber has at least nine
    // characters that can be converted to a 64 bit integer.
    if (mobileNumber.Length < 9)
        return false;

    long number;
    if (!long.TryParse(mobileNumber.Substring(0,9), out number))
        return false;

    // You can avoid writing the loop yourself and use LINQ instead.
    return numberRange.Any(r => number >= r.RangeStart && number < r.RangeEnd);
}

虽然我在上面使用过的Enumerable.Any扩展方法在本质上将对以下内容执行相同的操作:

代码语言:javascript
运行
复制
foreach (var item in numberRange)
    if (number >= item.RangeStart && number < item.RangeEnd)
        return true;

return false;

为什么我要改变numberRange的类型?

  • 因为除非您想要操作集合,否则不需要IList<T>。如果您只想枚举它,那么IEnumerable<T>就足够了。使用此签名,您可以将List<T>实例或任何其他IEnumerable<T>实例(例如数组或HashSet<T> )传递给此方法。

为什么我在前两次检查中抛出异常,而在其他人中返回错误?

  • 因为大多数情况下,空参数意味着代码中有错误,而空集合则没有。我建议将mobileNumber作为Int64传递,完全避免在此方法中进行转换。

我为什么要更改你的变量名?

  • 要获得可读性:,请参阅MSDN的大写风格页面中的类库开发人员命名指南部分。
票数 1
EN

Code Review用户

发布于 2012-10-28 08:08:39

代码语言:javascript
运行
复制
public bool CheckMobileSim(List<Mobile_Range> numberRange, string MobileNumber)
{
    var digits = new List<long>();
    for (int i = 5; i < 10; i++)
        digits.Add(Convert.ToInt64(MobileNumber.Substring(0, i).ToString()));

    return numberRange != null &&
        numberRange.Any(nr => digits.Any(n => n >= nr.RangeStart && n < nr.RangeEnd));
}

这样,您不需要一个循环,但后面有一个循环。

票数 0
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/18008

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档