首页 > 编程语言 >算法题 - Shuffling Machine

算法题 - Shuffling Machine

时间:2024-03-10 19:56:38浏览次数:17  
标签:Shuffling int 54 MAXSIZE Machine ++ 算法 cards orders

Introduction:
Shuffling is a procedure used to randomize a deck of playing cards. Because standard shuffling techniques are seen as weak, and in order to avoid "inside jobs" where employees collaborate with gamblers by performing inadequate shuffles, many casinos employ automatic shuffling machines. Your task is to simulate a shuffling machine.

The machine shuffles a deck of 54 cards according to a given random order and repeats for a given number of times. It is assumed that the initial status of a card deck is in the following order:

S1, S2, ..., S13,
H1, H2, ..., H13,
C1, C2, ..., C13,
D1, D2, ..., D13,
J1, J2

where "S" stands for "Spade", "H" for "Heart", "C" for "Club", "D" for "Diamond", and "J" for "Joker". A given order is a permutation of distinct integers in [1, 54]. If the number at the i-th position is j, it means to move the card from position i to position j. For example, suppose we only have 5 cards: S3, H5, C1, D13 and J2. Given a shuffling order {4, 2, 5, 3, 1}, the result will be: J2, H5, D13, S3, C1. If we are to repeat the shuffling again, the result will be: C1, H5, S3, J2, D13.
Input Specification:
Each input file contains one test case. For each case, the first line contains a positive integer K (≤20) which is the number of repeat times. Then the next line contains the given order. All the numbers in a line are separated by a space.
Output Specification:
For each test case, print the shuffling results in one line. All the cards are separated by a space, and there must be no extra space at the end of the line.
Sample Input:
2
36 52 37 38 3 39 40 53 54 41 11 12 13 42 43 44 2 4 23 24 25 26 27 6 7 8 48 49 50 51 9 10 14 15 16 5 17 18 19 1 20 21 22 28 29 30 31 32 33 34 35 45 46 47
Sample Output:
S7 C11 C10 C12 S1 H7 H8 H9 D8 D9 S11 S12 S13 D10 D11 D12 S3 S4 S6 S10 H1 H2 C13 D2 D3 D4 H6 H3 D13 J1 J2 C1 C2 C3 C4 D1 S5 H5 H11 H12 C6 C7 C8 C9 S2 S8 S9 H10 D5 D6 D7 H4 H13 C5

首先理解一下题目:

我们有一副有序的扑克牌(int[54]),需要拿到一组指令集(int[54]),和指令集执行次数(int),然后按照指令集交换卡牌的位置,最后输出卡牌的位置

输入:

1个整数,1个长度为54的数组

过程:

  1. 生成一个长度为54的有序数组,数据从1-54按升序排列
  2. 然后进行若干次循环,交换卡牌的位置

输出:

打印出卡牌的“花色”和“数字”

额外想法:

  • 把卡牌抽象成1-54,最后用字典来输出。这样可以简化卡牌的生成,专心实现卡牌交换
  • 把卡牌数54抽象到一个固定变量MAXSIZE,增加复用的可能

抽象实现:

#include <stdio.h>
const int MAXSIZE = 54;

int initOrders(int orders[]);
int initCards(int cards[]);
int exchangeCards(int cards[], int orders[], int repeatCount);
void outputWithDictionary(int output);

int main()
{
    int cards[MAXSIZE];
    int orders[MAXSIZE];
    int repeatCount = 0;

    // Input count and orders
    scanf("%d", &repeatCount);
    initOrders(orders);

    // Initialize cards
    initCards(cards);

    // Process
    exchangeCards(cards, orders, repeatCount);

    // Output cards
    for (int i = 0; i < MAXSIZE; i++)
    {
        int output = cards[i];
        outputWithDictionary(output);
        if (i < MAXSIZE - 1)
        {
            printf(" ");
        }
    }
}

然后是过程的具体实现

读取指令:for循环

点击查看代码
int initOrders(int orders[])
{
    for (int i = 0; i < MAXSIZE; i++)
    {
        scanf("%d", &orders[i]);
    }
    // for (int i = 0; i < MAXSIZE; i++)
    // {
    //     printf("%d ", orders[i]);
    // }
    // printf("\n");
    return 0;
}

初始化卡牌: for循环

点击查看代码
int initCards(int cards[])
{
    for (int i = 0; i < MAXSIZE; i++)
    {
        cards[i] = i + 1;
    }
    // for (int i = 0; i < MAXSIZE; i++)
    // {
    //     printf("%d ", cards[i]);
    // }
    // printf("\n");
    return 0;
}

交换卡牌:

  • 使用了一个中介的数组,保存卡牌按照指令修改后的位置。然后用for循环依次扫描填入后,再将临时数组的内容放回卡牌数组中。复杂度O(2N)=>O(N)
点击查看代码

int exchangeCards(int cards[], int orders[], int repeatCount)
{
    int temps[MAXSIZE] = {0};
    for (int i = 0; i < repeatCount; i++)
    {
        for (int j = 0; j < MAXSIZE; j++)
        {
            temps[orders[j] - 1] = cards[j];
        }
        for (int j = 0; j < MAXSIZE; j++)
        {
            cards[j] = temps[j];
        }
    }
    return 0;
}

输出字典:

  • 每13张更换一次色号——首字母,大小王各1张(J1,J2)。用If判断简单实现,switch也行。
点击查看代码
void outputWithDictionary(int output)
{
    if (output <= 13)
    {
        printf("S%d", output);
    }
    else if (output <= 26)
    {
        printf("H%d", output - 13);
    }
    else if (output <= 39)
    {
        printf("C%d", output - 26);
    }
    else if (output <= 52)
    {
        printf("D%d", output - 39);
    }
    else if (output <= 54)
    {
        printf("J%d", output - 52);
    }
}

完整代码

#include <stdio.h>
const int MAXSIZE = 54;

int initOrders(int orders[]);
int initCards(int cards[]);
int exchangeCards(int cards[], int orders[], int repeatCount);
void outputWithDictionary(int output);

int main()
{
    int cards[MAXSIZE];
    int orders[MAXSIZE];
    int repeatCount = 0;

    // Input count and orders
    scanf("%d", &repeatCount);
    initOrders(orders);

    // Initialize cards
    initCards(cards);

    // Process
    exchangeCards(cards, orders, repeatCount);

    // Output cards
    for (int i = 0; i < MAXSIZE; i++)
    {
        int output = cards[i];
        outputWithDictionary(output);
        if (i < MAXSIZE - 1)
        {
            printf(" ");
        }
    }
}

int initOrders(int orders[])
{
    for (int i = 0; i < MAXSIZE; i++)
    {
        scanf("%d", &orders[i]);
    }
    // for (int i = 0; i < MAXSIZE; i++)
    // {
    //     printf("%d ", orders[i]);
    // }
    // printf("\n");
    return 0;
}

int initCards(int cards[])
{
    for (int i = 0; i < MAXSIZE; i++)
    {
        cards[i] = i + 1;
    }
    // for (int i = 0; i < MAXSIZE; i++)
    // {
    //     printf("%d ", cards[i]);
    // }
    // printf("\n");
    return 0;
}

int exchangeCards(int cards[], int orders[], int repeatCount)
{
    int temps[MAXSIZE] = {0};
    for (int i = 0; i < repeatCount; i++)
    {
        for (int j = 0; j < MAXSIZE; j++)
        {
            temps[orders[j] - 1] = cards[j];
        }
        for (int j = 0; j < MAXSIZE; j++)
        {
            cards[j] = temps[j];
        }
    }
    return 0;
}

void outputWithDictionary(int output)
{
    if (output <= 13)
    {
        printf("S%d", output);
    }
    else if (output <= 26)
    {
        printf("H%d", output - 13);
    }
    else if (output <= 39)
    {
        printf("C%d", output - 26);
    }
    else if (output <= 52)
    {
        printf("D%d", output - 39);
    }
    else if (output <= 54)
    {
        printf("J%d", output - 52);
    }
}

标签:Shuffling,int,54,MAXSIZE,Machine,++,算法,cards,orders
From: https://www.cnblogs.com/Cloudea/p/18064687

相关文章

  • 算法学习
    今天复习巩固了深搜和广度搜索,做了几个练习题,其中求细胞数量注意审题,即让我们求连通块的个数。#include<bits/stdc++.h>usingnamespacestd;intx,y;charm[105][105];intsx[4]={-1,0,1,0};//左上右下intsy[4]={0,-1,0,1};voidbfs(inta,intb){ m[a][b]='0'; for(......
  • RIPEMD算法:多功能哈希算法的瑰宝
    一、RIPEMD算法的起源与历程RIPEMD(RACEIntegrityPrimitivesEvaluationMessageDigest)算法是由欧洲研究项目RACE发起,由HansDobbertin、AntoonBosselaers和VincentRijmen共同设计的一种哈希算法。RIPEMD算法最早发布于1996年,旨在提供一种安全、高效的数据完整性验证工具。......
  • 贪心算法
    例题1、硕鼠的交易题目描述ProblemDescription小老鼠准备了M磅的猫粮,准备去和看守仓库的猫做交易,因为仓库里有小老鼠喜欢吃的五香豆。仓库有N个房间;第i个房间有J[i]磅的五香豆,并且需要用F[i]磅的猫粮去交换;老鼠不必交换该房间所有的五香豆,换句话说,它可以用F[i]a%磅的......
  • 基于肤色模型和中值滤波的手部检测算法FPGA实现,包括tb测试文件和MATLAB辅助验证
    1.算法运行效果图预览RTL图:   仿真图:   导入到matlab显示效果如下:   2.算法运行软件版本matlab2022a vivado2019.2 3.算法理论概述      在计算机视觉领域,基于肤色模型和中值滤波的手部检测方法是一种常见的初步定位策略。该方法主要分为......
  • ST算法
    记录9:212024-3-10ST算法其实就是利用倍增的思想去划分区间利用ST算法求RMQ问题(区间最值问题)\(F[i,j]表示数列A在子区间[i,i+2^j-1]里数的最大值F[i,0]=A[i]\)\(F[i,j]=max(F[i,j-1],F[i+2^{j-1},j-1])\)求[l,r]最值的时候求出满足\(2^k<r-l......
  • KMP算法(基于代码随想录)的随笔
    KMPKMP的主要思想是当出现字符串不匹配时,可以知道一部分之前已经匹配的文本内容,可以利用这些信息避免从头再去做匹配了。前缀表:起始位置到下标i之前(包括i)的子串中,有多大长度的相同前缀后缀。那么使用KMP可以解决两类经典问题:匹配问题:28.实现strStr()(opensnewwindow)重......
  • SHA算法:数据完整性的守护者
    一、SHA算法的起源与演进SHA(SecureHashAlgorithm)算法是一种哈希算法,最初由美国国家安全局(NSA)设计并由国家标准技术研究所(NIST)发布。SHA算法的目的是生成数据的哈希值,用于验证数据的完整性和真实性。最早的SHA-0版本于1993年发布,之后陆续发布了SHA-1、SHA-2和SHA-3等不同版本,不......
  • Hanoi问题及其相关快速算法
    Hanoi问题抽象hanoi(n,x,y,z)step1:hanoi(n-1,x,z,y)step2:move(x,z)step3:hanoi(n-1,y,x,z)递归部分实现代码voidhanoi(intn,charx,chary,charz){​ if(n==1){ // 递归出口​ move(x,z);​ }​ else{​ hanoi(n-1,x,z,y);​ move(x,z);​ hanoi(n......
  • 基于Harris角点的室内三维全景图拼接算法matlab仿真
    1.算法运行效果图预览   2.算法运行软件版本matlab2022a 3.算法理论概述      在室内三维全景图的构建中,Harris角点检测算法扮演着关键的角色,用于识别场景中的特征点以实现图像间的匹配和对齐。该过程通常包括以下几个步骤:图像获取、角点检测、特征描述、匹......
  • JAVA使用DFA算法过滤敏感词
    代码示例如下:importcn.hutool.core.collection.CollUtil;importcn.hutool.core.util.ReUtil;importcn.hutool.core.util.StrUtil;importcom.google.common.collect.Lists;importcom.google.common.collect.Maps;importjava.util.*;publicclassSensitiveWordUtils......