c语言编程问题 求助大佬

背景:
假设要生成前n个自然数的一个随机置换,如{4,3,1,5,2}和{3,1,4,2,5}就是一个合法置换;
但{5,4,1,2,1}就不是,因为1出现2次而3没有。假设我们有一个随机数生成器RandInt(i,j),它以相同概率生成i到j之间的整数,
下面是三个算法。
(1) 如下填入从A[0]到A[N-1]的数组A:为了填入A[i],生成不同于A[0],A[1],...,A[i-1]之间的随机数时,才将其填入A[i]
(2) 同算法1,但保留一个称为Used数组的附加数组,当一个随机数Ram最初被放入数组A的时候,Used[Ram]=1.这就是说,
当用一个随机数填入A[i]时,用Used数组来测试该随机数是否已经被使用。
(3) 首先填写数组使得A[i]=i+1;然后
For(i=1;i<N;i++)
Swap(&A[i],&A[RandInt(0,i)])

要求实现以上三个算法的函数:(1对应(1)中的算法,请务必不要弄混)
void RandomPermutation1(int n);
void RandomPermutation2(int n);
void RandomPermutation3(int n);
在函数中输出为前n个自然数的一个随机置换,用,号分隔
必须使用教师提供的随机函数,函数原型如下:
int RandInt(int i, int j);
在文件中加入:extern int RandInt(int i, int j); 即可
(在测试的时候可以使用random函数,但是在向系统提交时必须改成调用RandInt产生随机数)

注意:
1、逗号为英文输入法中逗号;
2、输入n不为正整数时,输出error
3、在输出的结果后多输出",0"(不含外侧引号)表示输出结束,除此之外,其余任意多余输出视为错误。
例如:
1.当参数n = 5时,
输出格式为
1,2,3,4,5,0
2.例如n = 10时,数组的10个元素输出为2,8,5,1,10,9,3,6,7,4,但是需在结果后增加一个0
因此最终输出为:
2,8,5,1,10,9,3,6,7,4,0

第1个回答  2018-11-07
#include <iostream>
using namespace std;

extern int RandInt(int i, int j); //老师的随机函数
void RandomPermutation1(int n);   //方法一的函数
void RandomPermutation2(int n);   //方法二的函数
void RandomPermutation3(int n);   //方法三的函数 
void Swap(int*a,int*b);           //两数交换函数

/*下面是主函数,主函数只是为了验证三个方法的正确性,值可以自己修改*/
int main()                        //主函数
{RandomPermutation1(8);           //调用方法1
 printf("\n");                    //输出结束符0
 RandomPermutation2(8);           //调用方法1 
 printf("\n");                    //输出结束符0
 RandomPermutation3(8);           //调用方法1 
 printf("\n");                    //输出结束符0
 system("PAUSE");                 //屏幕暂停,以看清运行结果
 return 0;}                       //程序结束
 
/*方法一的函数主体*/
 void RandomPermutation1(int n)    //方法一
{int i,j,*A;                      //定义两个循环变量和一个数组指针
 if(n<=0)                         //如果n不是正整数
   {printf("error");return ;}     //输出error,并结束函数
 A=new int[n];                    //分配一个长度为n的整型数组
 for(i=0;i<n;i++)                 //逐个产生随机数
    {A[i]=RandInt(1,n);           //随机产生1-n之间的数
     for(j=0;j<i;j++)             //逐个和之前的做比较
         if(A[i]==A[j]) break;    //如果发现相等退出循环
     if(j<i) i--;                 //如果发现有相同,i=i-1,重新产生随机数
     else printf("%d,",A[i]);}    //否则输出A[i] 
 printf("0");                     //输出结束符0
 delete A;                        //函数结束前释放掉数组
 return ;}                        //函数结束
 
/*方法二的函数主体*/
void RandomPermutation2(int n)    //方法二
{int i,j,*A;                      //定义两个循环变量和一个数组指针
 bool *Used;                      //Used数组
 if(n<=0)                         //如果n不是正整数
   {printf("error");return ;}     //输出error,并结束函数
 A=new int[n];                    //分配一个长度为n的整型数组
 Used=new bool[n];                //分配一个长度为n的整型数组
 for(i=0;i<n;i++) Used[i]=false;  //初始化使用标志
 for(i=0;i<n;i++)                 //逐个产生随机数
    {while(Used[j=RandInt(1,n)-1]);//随机产生1-n之间没有使用过的随机数
     A[i]=j+1;                    //把随机数赋给A[i]
     Used[j]=true;                //作上已使用的标记
     printf("%d,",A[i]);}         //输出A[i] 
 printf("0");                     //输出结束符0
 delete A;                        //函数结束前释放掉数组
 delete Used;                     //函数结束前释放掉数组
 return ;}                        //函数结束
 
/*方法三的函数主体*/
void RandomPermutation3(int n)    //方法三
{int i,*A;                        //定义一个循环变量和一个数组指针
 if(n<=0)                         //如果n不是正整数
   {printf("error");return ;}     //输出error,并结束函数
 A=new int[n];                    //分配一个长度为n的整型数组
 for(i=0;i<n;i++) A[i]=i+1;       //初始化数组
 for(i=1;i<n;i++)                 //用一个循环
     Swap(&A[i],&A[RandInt(0,i)]);//把A[i]和其中一个随机调换
 for(i=0;i<n;i++)                 //逐个输出
     printf("%d,",A[i]);          //输出A[i] 
 printf("0");                     //输出结束符0
 delete A;                        //函数结束前释放掉数组
 return ;}                        //函数结束

/*交换函数主体*/ 
void Swap(int *a,int *b)          //两数交换函数
{int c;                           //中间变量c
 c=*a;                            //保存a指向的值
 *a=*b;                           //让a指向的值等于b指向的值
 *b=c;}                           //让b指向的值等于a原来的值

/*以下是老师提供的随机函数,这里为了方便调试也一并写出来*/
int RandInt(int i,int j)          //这是老师的随机函数,可以不用写
{static bool a=true;              //通过静态变量,控制函数首次调用种随机种子
 if(a) {srand(time(0));a=0;}      //如果函数首次调用,种一个随机种子
 if(i==j) return i;               //如果i等于j,则函数直接返回i
 if(i<j) return i+rand()%(j-i+1); //获得i-j之间的随机数 
 else return j+rand()%(i-j+1);}   //获得j-i之间的随机数

本回答被网友采纳