并行性比常规的foreach花费更多的时间

时间:2015-11-09 09:53:40

标签: c# .net parallel-processing

我希望通过添加并行功能来改进我的凯撒密码,但进一步的代码测量表明,并行方法比普通方法需要更多的时间来完成。

为什么?

正常

public string CaesarEncrypt(string text, int positions, char[] charSet = null) {

    if (string.IsNullOrEmpty(charSet)) {
        charSet = ("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789").ToCharArray();
    }

    List<char> charList = charSet.ToList();
    StringBuilder sb = new StringBuilder { Capacity = text.Length };

    foreach (char c in text) {
        int charPos = charList.IndexOf(c);

        if ((charPos == -1)) {
            sb.Append(c);
        } else {
            while (!(((charPos + positions) < (charSet.Length)))) {
                charPos -= charSet.Length;
            }
            sb.Append(charSet(charPos + positions));
        }
    }
    return sb.ToString();
}

平行

public string CaesarEncrypt(string text, int positions, char[] charSet = null) {

    if (string.IsNullOrEmpty(charSet)) {
        charSet = ("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789").ToCharArray();
    }

    List<char> charList = charSet.ToList();
    StringBuilder sb = new StringBuilder { Capacity = text.Length };

    Parallel.ForEach(text.ToArray(), (char c) =>
    {
        int charPos = charList.IndexOf(c);

        if ((charPos == -1)) {
            sb.Append(c);

        } else {
            while (!(((charPos + positions) < (charSet.Length)))) {
                charPos -= charSet.Length;
            }
            sb.Append(charSet(charPos + positions));

        }
    });
    return sb.ToString();
}

1 个答案:

答案 0 :(得分:3)

多线程的管理有一些成本。如果循环体中的任务太小,则此开销可能大于多线程的增益。

此处的另一个问题是,如果并行正文,则在StringBuilder内附加{。}}。由于无法保证线程完成的顺序,最终可能会得到一个混乱的结果。