python - 编程挑战时耗时高,效率低

时间:2016-04-05 10:24:21

标签: python algorithm python-2.7

我试图解决this problem.

  

最近Oz发现了一个由单个数字" 1"组成的神奇字符串。在对字符串进行实验之后,Oz发现了一个奇怪的字符串的魔法属性,即每当他触摸字符串然后每个数字" 1"字符串更改为数字" 0"和每个数字" 0"字符串更改为" 01"。 Oz发现这个属性很有趣,并立即向RK提出一个问题:"如果他接触字符串M次,那么多少1和0将会出现在神奇的字符串中?"

我为它编写了以下代码:

l = [] #List of values

for x in range(int(raw_input())):
    l.append(int(raw_input()))

def after_touchs(n, string): #Main function finds the no. of 0's and 1's
    for x in range(n):
        string = string.replace('1', '2').replace('0', '01').replace('2', '0')

    return map(str, [string.count('1'), string.count('0')])

for num in l:
    print ' '.join(after_touchs(num, '1'))

我不明白为什么这段代码需要花费很多时间。对我来说,它似乎完全正常,并没有花太多时间。因为它没有在网站上工作并且在我的计算机上使用解释器运行代码,甚至50的输入似乎也很大。 string.replace函数是否占用了太多时间?那么我可以使用哪些替代品呢?请帮我减少时间消耗并提高代码效率。

4 个答案:

答案 0 :(得分:4)

你只需要计算1和0的数量,字符串操作总是很重,所以我想这会减慢你的速度。

number1 = 1
number0 = 0
for i in xrange(M):
    # 0 -> 01
    newnumber1 = number0
    # 1 -> 0 and 0 -> 01
    number0 += number1
    # we replace the number1 with the new number
    number1 = newnumber1
print "%d %d"%(number0,number1)

修改
我在Tim Stopfer的评论中看到了一个更有效的解决方案 事实上,第一次更换后,0和1的数量遵循fibonnacci序列。
1:101123
0:011235
M:012345

O(1)解决方案的意思是:

if M>0:
    number1 = Fibo(M-1)
    number0 = Fibo(M)

但您必须使用wikipedia

中找到的公式来近似Fibonnacci序列的值

答案 1 :(得分:2)

可能是因为您每次都要编辑字符串。 你基本上实现了斐波纳契数列,第50个数字是 50:12586269025 = 52×11×101×151×3001

所以你有一个这个长度的字符串,你可以对它应用几个字符串操作。 这可能会导致流程变慢。

我希望我能提供帮助。

答案 2 :(得分:1)

根据问题,前6个触摸的字符串将如下所示:

" 1"," 0"," 01"," 010"," 01001",&# 34; 01001010"," 0100101001001"

并且计数将是 1 0,0 1 1,1 1 1,2 2,3 3 3,5 5 这让我想起了斐波那契系列。 斐波那契数字迅速增加,因此你会得到很长的字符串,占用大量内存并且操作起来很慢。

如果你需要速度,那么只需计算斐波纳契数。 您还可以通过缓存已经计算的值来加速天真的斐波纳契,这样如果您已经知道该系列的第4和第5个元素,您可以快速计算出第6个。

答案 3 :(得分:0)

公共类MagicalString {

public static void main(String[] args) {

    String modifiedString = touchTheString();
    countOneAndZero(modifiedString);

}

private static void countOneAndZero(String modifiedString) {

    Map<Character,Integer> map = new HashMap<Character,Integer>();

    char [] data = modifiedString.toCharArray();
    for(char c : data) {

        if(map.containsKey(c)) {
            map.put(c, map.get(c)+1);
        }else {
            map.put(c, 1);
        }
    }
    System.out.println(map);

    System.out.println(map.get('0'));
    System.out.println(map.get('1'));

}

static String touchTheString() {
    String input = "1";
    int touch = 5;

    while (touch != 0) {
        StringBuffer br = new StringBuffer();
        char[] temp = input.toCharArray();
        for (char c : temp) {
            if (c == '0') {
                input = br.append("01").toString();
            } else if (c == '1') {
                input = br.append("0").toString();
            }

        }

        touch--;
    }
    System.out.println(input);
    return input;
}

}