首页 > 试题广场 >

怪异的洗牌

[编程题]怪异的洗牌
  • 热度指数:3998 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 64M,其他语言128M
  • 算法知识视频讲解
对于一副扑克牌,我们有多种不同的洗牌方式。一种方法是从中间某个位置分成两半,然后相交换,我们称之为移位(shift)。比如原来的次序是123456,从第4个位置交换,结果就是561234。这个方式其实就是数组的循环移位,为了多次进行这个操作,必须使用一种尽可能快的方法来编程实现。在本题目中,还引入另外一种洗牌方式,就是把前一半(如果总数是奇数,就是(n-1)/2)牌翻转过来,这种操作称之为翻转(flip)。在前面shift操作的结果上进行flip,结果就是165234。当然,如果是实际的扑克牌,直接翻转会造成正反面混在一起的,我们就不管那么多了。 给定n张牌,初始次序为从1到n,经过若干次的shift和flip操作后,结果会是什么样?

输入描述:
输入包括多组测试数据,每组数据的第一行包括两个数 n和k。n表示牌的数目,1<n<1000,k表示下面要进行的操作数量。随后的k行,每行一个整数x,1<=x<=n,表示从第几个位置开始移位。在每一次shift操作后都接一个flip操作。


输出描述:
对于输入的每组数据,计算经过给定的k次shift和flip操作后,各个位置的数值。并按次序在一行上输出所有牌张的值,每个数值(不包括最后一个)后面有一个空格。
示例1

输入

6 1
4
0 0

输出

1 6 5 2 3 4
def help(num , t):
    arr1 = []
    arr2 = []
    if len(num)%2 == 0:
        len1 = (len(num))//2
    else:
        len1 = (len(num)-1)//2
    arr1 = num[t:] + num[0:t]
    arr2 = arr1[:len1][::-1] + arr1[len1:]
    return arr2

while True:
    try:
        n, k = map(int,input().strip().split())
        if n == 0 and k == 0 :
            break
        b = [i for i in range(1, n+1)]
        for _ in range(k):
            x = int(input().strip())
            b = help(b, x)
        print(" ".join(map(str,b)))
            
    except:
        break

发表于 2020-04-12 18:39:15 回复(0)
def data(arr_index,k):
    lenth=len(arr_index)
    if lenth%2==0:
        index1=k-1
        index2=lenth//2
    else:
        index1=k-1
        index2=(lenth-1)//2
    arr1=[]
    arr2=[]
    arr1=arr_index[index1+1:]+arr_index[0:index1+1]
    arr2=arr1[0:index2][::-1]+arr1[index2:]
    return arr2
while True:
    try:
        n,k=map(int,input().strip().split(' '))
        arr_index=[i for i in range(1,n+1)]
        for i in range(k):
            k_index=int(input().strip())
            arr_index=data(arr_index,k_index)          
        print(' '.join(map(str,arr_index)))
    except:
        break
发表于 2019-08-23 09:54:34 回复(0)