约瑟夫环问题及python与c++实现效率对比

约瑟夫环是一个数学的应用问题:已知n个人(以编号1,2,3...n分别表示)围坐在一张圆桌周围。从编号为k的人开始报数,数到m的那个人出列;他的下一个人又从1开始报数,数到m的那个人又出列;依此规律重复下去,直到圆桌周围的人全部出列。

python实现:

# 单链表节点
class LinkNode:
    def __init__( self, value ):
        self.value = value
        self.next = None

# 创建循环单链表,值从1开始
def create_cycle( total ):
    head = LinkNode( 1 )
    prev = head
    index = 2
    while total - 1 > 0:
        curr = LinkNode( index )
        prev.next = curr
        prev = curr
        index += 1
        total -= 1
    curr.next = head
    return head

# 模拟约瑟夫环过程,从1开始计数
def run( total, tag ):
    assert total >= 0, ‘total lq 0‘
    assert tag >= 0, ‘tag lt 0‘
    node = create_cycle( total )
    prev = None
    start = 1
    index = start
    while node and node.next:
        if index == tag:
            print( node.value )
            if tag == start:
                prev = node.next
                node.next = None
                node = prev
            else:
                prev.next = node.next
                node.next = None
                node = prev.next
        else:
            prev = node
            node = node.next
            index += 1

run( 5, 999 )

c++实现如下:

// josephCycle.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include <stdlib.h>

typedef struct _LinkNode
{
    int value;
    struct _LinkNode* next;
}LinkNode, *LinkNodePtr;

LinkNodePtr createCycle( int total )
{
    int index = 1;
    LinkNodePtr head = NULL, curr = NULL, prev = NULL;
    head = (LinkNodePtr)malloc(sizeof(LinkNode));
    head->value = index;
    prev = head;

    while(--total > 0)
    {
        curr = (LinkNodePtr)malloc(sizeof(LinkNode));
        curr->value = ++index;
        prev->next = curr;
        prev = curr;
    }
    curr->next = head;
    return head;
}

void run( int total, int tag )
{
    LinkNodePtr node = createCycle( total );
    LinkNodePtr prev = NULL;
    int start = 1;
    int index = start;
    while(node && node->next)
    {
        if(index == tag)
        {
            printf("\n%d", node->value);
            if(tag == start)
            {
                prev = node->next;
                node->next = NULL;
                node = prev;
            }
            else
            {
                prev->next = node->next;
                node->next = NULL;
                node = prev->next;
            }
            index = start;
        }
        else
        {
            prev = node;
            node = node->next;
            index++;
        }
    }
}

int _tmain(int argc, _TCHAR* argv[])
{
    run( 5, 999999 );
    return 0;
}
时间: 2024-07-31 21:45:52

约瑟夫环问题及python与c++实现效率对比的相关文章

Python多进程与单进程效率对比

运行环境:Python3 in win10 先生成200个测试文件 # generate.py i = 0 while i < 200: o = open("test\\" + str(i) + ".py", "w") content = str(i) o.write(content) o.close() i += 1 多进程拷贝文件 # multi-pool-copy.py from multiprocessing import Pool

约瑟夫环问题python解法

约瑟夫环问题:已知n个人(以编号1,2,3...n分别表示)围坐在一张圆桌周围.从编号为k的人开始报数,数到k的那个人被杀掉:他的下一个人又从1开始报数,数到k的那个人又被杀掉:依此规律重复下去,直到圆桌周围的人只剩最后一个. 思路是:当k是1的时候,存活的是最后一个人,当k>=2的时候,构造一个n个元素的循环链表,然后依次杀掉第k个人,留下的最后一个是可以存活的人.代码如下: class Node(): def __init__(self,value,next=None): self.valu

趣味算法--约瑟夫环问题

问题描述 已知n个人(以编号1,2,3,...,n分别表示)围坐在一张圆桌上.指定编号为k的人开始从1报数,数到m的那个人出列:出列那个人的下一位又从1开始报数,数到m的那个人出列:以此规则重复下去,直到圆桌上的人全部出列. 分析解决 解决方法主要有逻辑分析.数学分析法. 逻辑分析:就是按照游戏规则一个个报数,报到m的人出局,结构层次简单清晰明了.这种方式实现主要采用顺序表实现 数学分析:采用数学方式归纳统计分析出每次出局人的规律,直接得出每次出局的人,然后以代码实现.这种方法需要较强的数学分析

一个不简洁的约瑟夫环解法

约瑟夫环类似模型:已知有n个人,每次间隔k个人剔除一个,求最后一个剩余的. 此解法为变种,k最初为k-2,之后每次都加1. 例:n=5,k=3.从1开始,第一次间隔k-2=1,将3剔除,第二次间隔k-1=2,将1剔除.依此类推,直至剩余最后一个元素. 核心思路:将原列表复制多份横向展开,每次根据间隔获取被剔除的元素,同时将此元素存入一个剔除列表中.若被剔除元素不存在于剔除列表,则将其加入,若已存在,则顺势后移至从未加入剔除列表的元素,并将其加入.如此重复n-1次.面试遇到的题,当时只写了思路,没

ytu 1067: 顺序排号(约瑟夫环)

1067: 顺序排号Time Limit: 1 Sec  Memory Limit: 128 MBSubmit: 31  Solved: 16[Submit][Status][Web Board] Description 有n人围成一圈,顺序排号.从第1个人开始报数(从1到3报数),凡报到3的人退出圈子,问最后留下的是原来的第几号的那位. Input 初始人数n Output 最后一人的初始编号 Sample Input 3 Sample Output 2 HINT Source freepro

约瑟夫环 C语言 单循环链表

/*---------约瑟夫环---------*/ /*---------问题描述---------*/ /*编号为1,2,-,n的n个人围坐一圈,每人持一个密码(正整数). 一开始任选一个正整数作为报数上限值m, 从第一个人开始自1开始顺序报数,报到m时停止. 报m的人出列,将他的密码作为新的m值,从他的下一个人开始重新从1报数, 如此下去,直至所有人全部出列为止.试设计一个程序求出列顺序.*/ /*---------问题分析---------*/ /*n个人围坐一圈,且不断有人出列,即频繁

循环单向链表(约瑟夫环)

#include <stdio.h> #include <stdlib.h> typedef struct List { int data; struct List *next; }List; //创建循环单向链表n为长度 List *list_create(int n) { List *head, *p; int i; head = (List *)malloc(sizeof(List)); p = head; p->data = 1; //创建第一个结点 for (i =

约瑟夫环问题

(约瑟夫环问题)有n个人围成一圈,顺序排号.从第一个人开始报数(从1到3报数),凡报到3的人退出圈子,问最后留下的是原来第几号的那个人. package aiqiyi; import java.util.ArrayList; public class Main { public static int leftPerson(int n) { // 用list来保存n个人,序号为1~n ArrayList<Integer> list = new ArrayList<Integer>()

cdoj525-猴子选大王 (约瑟夫环)

http://acm.uestc.edu.cn/#/problem/show/525 猴子选大王 Time Limit: 3000/1000MS (Java/Others)     Memory Limit: 65535/65535KB (Java/Others) Submit Status 有m个猴子围成一圈,按顺时针编号,分别为1到m.现打算从中选出一个大王.经过协商,决定选大王的规则如下:从第一个开始顺时针报数,报到n的猴子出圈,紧接着从下一个又从1顺时针循环报数,...,如此下去,最后剩