关于python:不使用reverse()或[:: – 1]反转字符串?

Reverse a string without using reversed() or [::-1]?

我遇到了一个奇怪的codecademy练习,它需要一个将字符串作为输入并按相反顺序返回的函数。唯一的问题是您不能在stackoverflow上使用反向方法或常见的答案,[::-1]

显然,在编程的现实世界中,很可能会使用扩展切片方法,甚至使用reversed函数,但在某些情况下,这可能不起作用?

我在下面以问答的方式提出了一个解决方案,以防将来对人们有所帮助。


您还可以使用递归进行此操作:

1
2
3
4
5
def reverse(text):
    if len(text) <= 1:
        return text

    return reverse(text[1:]) + text[0]

以及字符串hello的简单示例:

1
2
3
4
5
6
7
   reverse(hello)
 = reverse(ello) + h           # The recursive step
 = reverse(llo) + e + h
 = reverse(lo) + l + e + h
 = reverse(o) + l + l + e + h  # Base case
 = o + l + l + e + h
 = olleh


只是另一个选择:

1
2
3
4
5
from collections import deque
def reverse(iterable):
    d = deque()
    d.extendleft(iterable)
    return ''.join(d)


使用反向range

1
2
3
4
5
6
def reverse(strs):
    for i in xrange(len(strs)-1, -1, -1):
        yield strs[i]
...        
>>> ''.join(reverse('hello'))
'olleh'

带-1步的xrangerange将按相反的顺序返回项目,因此我们需要从len(string)-1迭代到-1并逐个从字符串中提取项目。

1
2
>>> list(xrange(len(strs) -1, -1 , -1))
[4, 3, 2, 1, 0]  #iterate over these indexes and fetch the items from the string

一班轮:

1
2
3
4
5
def reverse(strs):
    return ''.join([strs[i] for i in xrange(len(strs)-1, -1, -1)])
...
>>> reverse('hello')
'olleh'


编辑

最近关于这个问题的活动使我回顾并将我的解决方案更改为使用发电机的快速一行程序:

1
rev = ''.join([text[len(text) - count] for count in xrange(1,len(text)+1)])

虽然很明显这里有一些更好的答案,比如范围内的负阶跃或xrange函数。以下是我的原始解决方案:

这是我的解决方案,我将逐步解释

1
2
3
4
5
6
7
8
9
10
11
12
13
14
def reverse(text):

    lst = []
    count = 1

    for i in range(0,len(text)):

        lst.append(text[len(text)-count])
        count += 1

    lst = ''.join(lst)
    return lst

print reverse('hello')

首先,我们必须向函数传递一个参数,在本例中是text

接下来,我设置了一个空列表,名为lst,供以后使用。(事实上,我不知道我需要这个列表,直到我到达for循环,你会明白为什么需要一秒钟。)

当我进入for循环时,count变量将是有意义的。

因此,让我们来看看我们正在努力实现的目标的基本版本:

将最后一个字符追加到列表中会以相反的顺序开始是有意义的。例如:

1
2
3
4
5
>>lst = []
>>word = 'foo'
>>lst.append(word[2])
>>print lst
['o']

但为了继续撤销订单,我们需要追加word[1],然后追加word[0]

1
2
3
4
5
>>lst.append(word[2])
>>lst.append(word[1])
>>lst.append(word[0])
>>print lst
['o','o','f']

这很好,我们现在有了一个列表,它将原始单词按相反的顺序排列,并且可以使用.join()将其转换回字符串。但有个问题。这适用于单词foo,它甚至适用于任何长度为3个字符的单词。但是一个有5个字符的词呢?还是10个字符?现在不行了。如果有一种方法可以动态地更改我们附加的索引,以便以相反的顺序返回任何单词,该怎么办?

输入循环。

1
2
3
4
for i in range(0,len(text)):

    lst.append(text[len(text)-count])
    count += 1

首先,有必要使用in range(),而不仅仅是in,因为我们需要迭代单词中的字符,但是我们还需要提取单词的索引值,以便更改顺序。

我们for循环体的第一部分应该看起来很熟悉。它非常类似于

1
>>lst.append(word[..index..])

事实上,它的基本概念完全相同:

1
>>lst.append(text[..index..])

那么中间的东西都在做什么呢?

好吧,我们需要首先在列表中附加最后一个字母的索引,它是单词的长度,text--1。从现在起我们称之为L(T)-1

1
>>lst.append(text[len(text)-1])

单凭这一点,我们就能得到单词的最后一个字母,并将其附加到lst,而不管单词的长度如何。但是现在我们有了最后一个字母,它是l(t)-1,我们需要第二个字母到最后一个字母,它是l(t)-2,依此类推,直到没有更多的字符附加到列表中。还记得我们上面的count变量吗?那会有用的。通过使用for循环,我们可以通过每次迭代将count的值增加1,从而使我们减去的值增加,直到for循环迭代整个单词:

1
2
3
4
>>for i in range(0,len(text)):
..        
..      lst.append(text[len(text)-count])
..      count += 1

既然我们已经拥有了我们的核心功能,那么让我们来看看目前为止我们所拥有的:

1
2
3
4
5
6
7
8
9
def reverse(text):

    lst = []
    count = 1

    for i in range(0,len(text)):

        lst.append(text[len(text)-count])
        count += 1

我们快结束了!现在,如果我们用"hello"这个词调用函数,我们会得到一个如下的列表:

[O'、'L'、'L'、'E'、'H']

我们不需要列表,我们需要一个字符串。我们可以使用.join来:

1
2
3
4
5
6
7
8
9
10
11
12
def reverse(text):

    lst = []
    count = 1

    for i in range(0,len(text)):

        lst.append(text[len(text)-count])
        count += 1

    lst = ''.join(lst) # join the letters together without a space
    return lst

就是这样。如果我们在reverse()上调用"hello"这个词,我们会得到:

1
2
>>print reverse('hello')
olleh

显然,这比现实生活中需要的代码要多。使用反向函数或扩展切片将是完成此任务的最佳方式,但可能有一些实例它不起作用,您需要这样做。不管怎样,我想我会把它分享给任何有兴趣的人。

如果你们还有别的想法,我很想听听!


只对Python进行了几天的编码,但我觉得这是一个相当干净的解决方案。创建一个空列表,循环遍历字符串中的每个字母,并将其附加到列表的前面,将联接的列表作为字符串返回。

1
2
3
4
5
def reverse(text):
backwardstext = []
for letter in text:
    backwardstext.insert(0, letter)
return ''.join(backwardstext)

我用过这个:

1
2
3
4
5
6
def reverse(text):
s=""
l=len(text)
for i in range(l):
    s+=text[l-1-i]
return s


这是一个非常有趣的问题,我想提出一个简单的问题线性回答:

1
2
3
>>> S='abcdefg'
>>> ''.join(item[1] for item in sorted(enumerate(S), reverse=True))
'gfedcba'

简要说明:

enumerate()返回[(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd'), (4, 'e'), (5, 'f'), (6, 'g')]。索引和值。要反转这些值,只需按sorted()对其进行反向排序。最后,把它放回一个str


受乔恩回答的启发,这个怎么样

1
2
3
word = 'hello'
q = deque(word)
''.join(q.pop() for _ in range(len(word)))

我在repo中创建了不同版本的如何在python中反转字符串:https://github.com/fedmich/python codes/tree/master/reverse%20a%20string

您可以通过使用列表理解或lambda技术来实现:

1
2
3
4
5
6
# Reverse a string without using reverse() function
s = 'Federico';
li = list( s )  #convert string to list

ret = [ li[i-1] for i in xrange(len(li),0,-1)  ]    #1 liner lambda
print ("".join( ret ) )

或者做一个反向for循环

1
2
3
4
5
6
7
8
9
# Reverse a string without using reverse() function
s = 'Federico';
r = []

length = len(s)
for i in xrange(length,0,-1):
    r.append( s[ i - 1] )

print ("".join(r) )


1
reduce(lambda x, y : y + x,"hello world")

Blender的回答是好的,但一个很长的字符串,它会导致一whopping RuntimeError: maximum recursion depth exceeded。一个可能的代码重构一个while循环是一样的,他们必须做一个Python递归。浴室很安静,由于时间和记忆的问题,但至少不会错误。

1
2
3
4
5
6
def reverse(text):
    answer =""
    while text:
        answer = text[0] + answer
        text = text[1:]
    return answer

golfed版本:r=lambda x:"".join(x[i] for i in range(len(x-1),-1,-1))


1
2
def reverse(s):
    return"".join(s[i] for i in range(len(s)-1, -1, -1))

我刚在代码学院解决了这个问题,正在检查我的答案,并浏览了这个列表。所以,由于对python的理解非常有限,我只做了这个,它运行起来非常顺利。

1
2
3
4
5
6
7
def reverse(s):
    i = len(s) - 1
    sNew = ''
    while  i >= 0:
        sNew = sNew + str(s[i])
        i = i -1
    return sNew


您可以简单地从最后一个字符开始反向迭代您的字符串。使用python,您可以使用列表理解以相反的顺序构造字符列表,然后将它们连接在一起,以在一行中获得颠倒的字符串:

1
2
def reverse(s):
  return"".join([s[-i-1] for i in xrange(len(s))])

如果不允许使用负索引,则应将s[-i-1]替换为s[len(s)-i-1]


我所做的就是使用xrange函数,其中字符串的长度为for循环,并按照以下步骤后退:

1
2
3
4
myString ="ABC"

for index in xrange(len(myString),-1):
    print index

我的输出是"cba"


1
2
3
4
5
6
7
def reverse(text):
    a=""
    l=len(text)
    while(l>=1):
        a+=text[l-1]
        l-=1
    return a

我只是将字符串A与最高的文本索引连接在一起(每个循环递减1)。


这是一种使用while循环的方法:

1
2
3
4
5
6
7
def reverse(s):
    t = -1
    s2 = ''
    while abs(t) < len(s) + 1:
        s2 = s2 + s[t]
        t  = t - 1
    return s2


今天有人问我在纸笔上做同样的练习,所以我想出了这个列表功能:

1
2
3
4
5
def rev(s):
  l = len(s)
  for i,j in zip(range(l-1, 0, -1), range(l//2)):
    s[i], s[j] = s[j], s[i]
  return s

可与带"".join(rev(list("hello")))的字符串一起使用


我刚刚解决了codeacademy上的相关问题,并希望将我的方法与其他方法进行比较。到目前为止,我还没有找到我使用的解决方案,所以我想我在这里注册并向其他人提供我的解决方案。也许我会得到一个关于如何改进代码的建议或有用的评论。

好了,我没有使用任何列表来存储字符串,只是访问了字符串索引。起初我花了一点时间来处理len()和索引号,但最终还是成功了:)。

1
2
3
4
5
def reverse(x):
reversestring =""
for n in range(len(str(x))-1,-1, -1):
    reversestring += x[n]
return reversestring

我仍然想知道是否可以用更优雅的方式来解决reversestring ="",或者它是否是"糟糕的风格",但到目前为止我还找不到答案。


1
2
3
4
5
6
7
def reverseThatString(theString):
    reversedString =""
    lenOfString = len(theString)
    for i,j in enumerate(theString):
        lenOfString -= 1
        reversedString += theString[lenOfString]
    return reversedString

这里是一个列表,作为一个堆栈的使用:

1
2
3
4
5
6
def reverse(s):
  rev = [_t for _t in s]
  t = ''
  while len(rev) != 0:
    t+=rev.pop()
  return t

这是我的解决方案中使用for循环:1范围

1
2
3
4
5
def reverse(string):
    tmp =""
    for i in range(1,len(string)+1):
        tmp += string[len(string)-i]            
    return tmp

这是很容易理解的。i从1开始以避免指数走出束缚。


你能做的就是这样的

1
2
3
4
5
def rev(str):
   rev =""
   for i in range(0,len(str)):
   rev = rev + str[(len(str)-1)-i]
   return rev


这里是我的贡献:

1
2
3
4
5
6
7
8
9
10
def rev(test):  
    test = list(test)
    i = len(test)-1
    result = []

    print test
    while i >= 0:
        result.append(test.pop(i))
        i -= 1
    return"".join(result)

您已经收到了很多备选答案,但只是为了添加另一个简单的解决方案——首先想到的是这样的问题:

1
2
3
4
5
6
7
def reverse(text):
    reversed_text =""  

    for n in range(len(text)):
        reversed_text += text[-1 - n]

    return reversed_text

它不像人们提到的其他一些选项(或内置方法)那么快,但很容易理解,因为我们只是使用text字符串的长度,通过从末尾向前切片,一次连接一个字符。


这是最简单的办法在Python 2.7语法

1
2
3
4
5
6
7
8
9
def reverse(text):

      rev =""
      final =""

      for a in range(0,len(text)):
            rev = text[len(text)-a-1]
            final = final + rev
return final

简单的方法

1
2
3
4
>>> a ="hi hello"
>>> ''.join([a[len(a)-i-1] for i,j in enumerate(a)])
'olleh ih'
>>>

你可以简单的使用AS内的流行。这是一个fot班轮

1
2
3
4
5
6
chaine = 'qwertyuiop'
''.join([chaine[-(x + 1)] for x in range(len(chaine))])
'poiuytrewq'
gg = list(chaine)
''.join([gg.pop() for _ in range(len(gg))])
'poiuytrewq'

我喜欢这是最好的方式使用一个倒一弦环。

1
2
3
4
5
6
7
8
def reverse_a_string(str):

    result=""
    for i in range(len(str),1,-1):
        result= result+ str[i-1]
    return result

print reverse_a_string(input())

1
2
3
4
5
6
7
8
9
10
11
12
13
enterString=input("Enter a string to be reversed:")
string_List=list(enterString)
revedString=[]

for i in range(len(string_List)):
    revedString.append(string_List.pop())
#Pop last element and append it to the empty list
print"reversed string is:",''.join(revedString)
#as the out come is in list convert it into string using .join

Sample Output:
>>>Enter a string to be reversed :sampleReverse1  
>>>reversed string is:1esreveRelpmas

你有足够的答案。

只想分享另一种方式。

您可以编写一个用于反转的两个小函数,并将函数输出与给定的字符串进行比较。

var=

DEF REVERSE(数据):

1
2
3
for i in data:
    var = i + var
return var

如果不是var==数据:

打印"无回文"

其他:

打印"回文"


我可以不使用任何内置功能的方式:

1
2
3
4
5
6
7
8
9
a = 'word'
count = 0
for letter in a:
    count += 1

b = ''
for letter in a:
    b += a[count-1]
    count -= 1

如果你打印B:

1
2
print b
drow

1
2
3
4
5
6
7
8
9
m = input("Enter string::")
def rev(s):
    z = -1
    x = len(s)
    while x != 0:
        print(s[z], end='')
        z = z-1
        x = x-1
rev(m)


不是很聪明,但很难解决

1
2
3
4
def reverse(t):
    for j in range(len(t) // 2):
        t = t[:j] + t[- j - 1] + t[j + 1:- j - 1] + t[j] + t[len(t) - j:]
    return t


我的解决方案:

_(S =原始输入"输入字符串")打印定义:反向(文本)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
st =""  
rev =""  
count = len(text)  
print"Lenght of text:", len(text)  
print  
for c in range(len(text)):  
    count = count - 1  
    st = st +"".join(text[c])  
    rev = rev +"".join(text[count])  
    print"count:      ", count  
    print"print c:    ", c  
    print"text[c]:    ", text[c]  
    print  
print"Original:   ", st  
print"Reversed:   ", rev  
return rev

反向(S)

结果屏幕

字符串和回车

长距离的文本:4

字数:3打印C:0文字:[ C ] J

字数:2打印C:1文字:[ C ]

字数:1印刷:2 C【C】C:文本

字数:0打印C:3文本[ C ]:A

原文:本反相:acojNONE


Pointfree:

1
2
3
4
5
from functools import partial
from operator import add

flip = lambda f: lambda x, y: f(y, x)
rev = partial(reduce, flip(add))

测试:

1
2
>>> rev('hello')
'olleh'

简单的运行,但它是在每个字符在一个单独的打印线的第二版,它在一个印刷线。

1
2
3
def rev(str):
        for i in range(0,len(str)):
            print(list(str)[len(str)-i-1])

在一个印刷线:

1
2
3
4
5
def rev(str):
    rev = list()
    for i in range(0,len(str)):
        rev.append((list(str)[len(str)-i-1]))
    print(''.join(rev))

我们可以先转换成一个字符串的字符串列表,然后在这之后使用"反向.join同体"再次转换到单字符串列表。

1
2
3
4
text="Youknowwhoiam"
lst=list(text)
lst.reverse()
print("".join(lst))

它会转换为第一youknowwhoiam"["Y",O,U,K,N,O,W,W,H,O,I,A,M〕

后它会反向列表和【m","a","I","O"、"H,W,W,O,N,K,U,O′y′],

它会在负载转换到Word"maiohwwonkuoy单列表"

更多的解释,只是在运行此代码的信:

1
2
3
4
5
6
text="Youknowwhoiam"
lst=list(text)
print (lst)
lst.reverse()
print(lst)
print("".join(lst))

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
__author__ = 'Sreedhar'
#find reverse of the string with out using index or reverse function?

def reverse(text):
    revs =""
    for i in text:
        revs = i + revs
    return revs

strig = raw_input("enter anything:")

print reverse(strig)

#index method
print strig[::-1]

最简单的方法来反求a的字符串:

1
2
    backwards = input("Enter string to reverse:")
    print(backwards[::-1])