首页 > 解决方案 > 设置运行长度编码长度的最小限制

问题描述

def encode (plainText):
    res=''
    a=''
    for i in plainText:
        if a.count(i)>0:
           a+=i
        else:
            if len(a)>3:
                res+="/" + str(len(a)) + a[0][:1]
            else:
                res+=a
                a=i
    return(res)

这是我当前的代码。对于那些了解运行长度编码的人来说,它可以使文件变大,因为一个值变成了两个。我正在尝试将最小长度设置为 3,以便它实际压缩。任何有关代码更正的帮助,非常感谢您的建议。

标签: pythonpython-3.7

解决方案


你在那里犯了很多错误,这里有一个小清单。

1  def encode (plainText):
2      res=''
3      a=''
4      for i in plainText:
5          if a.count(i)>0:
6             a+=i
7          else:
8              if len(a)>3:
9                  res+="/" + str(len(a)) + a[0][:1]
10             else:
11                 res+=a
12                 a=i
13     return(res)
  • 第 [3]、[5] 行:您将字母存储在一个字符串中并重复调用计数。简单地存储最后一个字符并添加新变量作为计数器会更容易(也更快)。
  • 第 [8][9] 行:只要遇到重复字符,就添加(正确的)编码字符串。但是,您永远不会更新a. 所以一旦你第一次到达这行代码,每个下一个字符都会添加相同的编码字符串。解决方案很简单,将 Line [12] 移动一个缩进,因此它在两种情况下都分配了新字符。
  • 第 [13] 行:您在不添加最后一个字符的情况下输出。迭代编码适用于前一个字符。这意味着必须在循环结束后处理字符串中的最后一个字符。
  • 最后但并非最不重要的一点是,由于您将/其用作特殊字符,因此当它作为非重复代码出现时,您应该以某种方式处理它。例如,明文/12a将被编码为/12a,然后被解码为 12a秒的序列。

这是一些(希望是)工作示例:

def encode (plainText):
    ## Lazy solution for some of the edge cases
    if plainText is None or len(plainText) == 0:
        return plainText

    ## We can join this together
    ## and have faster arbitrary 
    ## str length addition
    res=[]
    ## We only care about the last
    ## character, no need to save all
    prev_char=''
    ## And count it ourselves, its
    ## faster then calling count
    count=0
    for i in plainText:
        if i == prev_char:
            ## If its the same char
            ## increment count
            count += 1
            ## and then continue with next
            ## cycle. Avoid unneccasary indent.
            continue

        ## else
        if count > 2 or prev_char == '/':
            ## If more then 2 occurances
            ## we build the encoding.
            ## for 3 occurances the length is the same.
            ## '/' is a special character so we
            ## always encode it
            res.append(
                f"/{count}{prev_char}"
            )
        else:
            ## Otherwise just append the symbols
            res.append(prev_char*count)
        ## We observed at least 1 instance of i 
        count = 1
        ## Store for next comparison
        prev_char = i

    ## Now deal with last character.
    ## Without this your string would miss it.
    if count > 2 or prev_char == '/':
        res.append(
            f"/{count}{prev_char}"
        )
    else:
        res.append(prev_char*count)

    ## And build our string
    return ''.join(res)

推荐阅读