【问题标题】:More efficient looping? [closed]更有效的循环? [关闭]
【发布时间】:2013-03-18 02:22:40
【问题描述】:

所以我正在编写一个简单的结构来表现得像一个字符串数组,但有一些方便的运算符和其他我一直想在字符串中看到的函数。具体来说,我现在正在使用的方法是 / 运算符。 问题是,它不会像我想要的那样在最后添加任何余数。

它应该做的是获取一个字符串数组,例如 {"Hello", "Test1", "Test2", "Goodbye", "More?", "Qwerty"},假设我想除以 4,它应该返回 { {"Hello", "Test1", "Test2", "Goodbye"}, {"More?", "Qwerty"} },但它没有。

整个班级(我想改进的方法是 / 运算符,但如果您看到我可以做的其他工作,请指出)(我知道几乎没有任何评论。抱歉,没有期望除我之外的其他人看到此代码。):

public struct StringCollection
{
    private String[] value;

    public StringCollection(params String[] s)
    {
        this.value = s;
    }

    public StringCollection(StringCollection current, String ad)
    {
        if (current.value == null) {
            current.value = new String[0] { };
        }
        this.value = new String[current.value.Length+1];
            for (int i=0; i<this.value.Length; i++)
            {
                try {
                    this.value[i] = current[i];
                } catch {
                    break;
                }
            }
            this.value[this.value.Length-1] = ad;
    }
    public StringCollection(StringCollection x, params StringCollection[] y)
    {
        this.value = x.value;
        for (int j=0;j<y.Length;j++)
        {
            for (int i=0;i<y[j].value.Length;i++)
            {
                this += y[j][i];
            }
        }
    }

    public static StringCollection[] operator /(StringCollection x, int y)
    {
        StringCollection[] result = null;
        if (((int)x.value.Length/y) == ((double)x.value.Length)/y)
            result = new StringCollection[y];
        else
            result = new StringCollection[y+1];
        for (int j=0;j<y;j++)
        {
            for (int i=0;i<((int)x.value.Length/y);i++)
            {
                result[j] += x.value[i+(int)((x.value.Length/y)*j)];
            }
        }
        if (((int)x.value.Length/y) != ((double)x.value.Length)/y)
        {
                            // This is the part that isn't working.
            for (int i=0;i<(((int)x.value.Length/y)*result[0].value.Length)-x.value.Length;i++) 
            {
                result[result.Length-1] += x.value[i+((result[0].value.Length)*result.Length-2)];
            }
        }
        return result;
    }
    public String this[int index]
    {
        get {
            return this.value[index];
        }
        set {
            this.value[index] = value;
        }
    }

}

它所做的基本上是将您的数组(单个数组)拆分为一组大小相同的数组,然后在最后将剩余部分添加到一个新数组中。

【问题讨论】:

  • 这不是这个特定问题的地方,也许您正在寻找Code Review
  • @DJKRAZE 这也可能在代码审查时被关闭,因为他正在询问一个特定的问题。代码审查通常假定工作代码并询问如何最好地重构。此代码工作,他想知道如何修复它。
  • 也就是说,这个问题也不适合所问的 Stack Overflow。要成为一个有效的 SO 问题,我们需要具体了解问题是什么以及如何重现它。
  • 你们部门的逻辑是什么?你怎么能问“x 会进入 y 多少次?”这个问题?字符串和整数除法一样吗?
  • @Winderps:实际上吞下异常或在控制流中使用 try-catch 是一种不好的做法(只是给出一个原因,try-catch 在捕获异常时是一项非常昂贵的操作)所以你应该检查数组的长度并避免它...

标签: c# arrays string loops operators


【解决方案1】:

首先,您的问题根本与循环无关,或者至少循环仅在您的代码中得到解决。你应该给它取个不同的标题。

其次,可以改进您的阵列添加/删除;即每次将 1 添加到数组大小并删除 1 然后每次重新复制整个数组是一个时间接收器。

现在回答你的问题,你的代码基本上应该是这样的:

//Make your return array
int retLen = x.Length / y;      

//Add space for the remainder
if(x.Length % y != 0)
  retLen++;

var ret = new StringCollection[retLen];

//Reusing variables is a good way to save memory, but watch naming conventions as this can be confusing
retLen = 0;

var tempCollection = new StringCollection();

for (int i = 0; i < x.Length; i++)
{
  tempCollection = new StringCollection(tempCollection, x[i]);

  if(i % y == 0 || i == x.Length - 1)
  {
    ret[retLen++] = tempCollection;
    tempCollection = new StringCollection();
    retLen = 0;
  }    
}

return ret;

我真的不喜欢你在这个结构中没有 Add 函数,这样我们就清楚了。 tempCollection = new StringCollection(tempCollection, x[i]); 在创建所有这些新对象的 CPU 时间方面非常糟糕。

很确定你需要调整它以确保正确输入所有项目,但这是第一次尝试,所以......嗯 oO 想,因为实际上没有人会回答你我会花时间.

编辑:发现一个错误,添加到 ret 时忘记将 retLen 设置回 0

【讨论】:

  • 谢谢你!哇,与你的代码相比,我的看起来像意大利面条。从现在开始我将使用它。 :D
猜你喜欢
  • 2013-02-22
  • 1970-01-01
  • 2013-04-09
  • 2016-04-14
  • 1970-01-01
  • 1970-01-01
  • 2016-04-15
  • 2020-09-17
  • 1970-01-01
相关资源
最近更新 更多