您的位置:首页 > 其它

[经典算法] 排列组合-全排序

2015-09-24 18:11 288 查看

题目说明:

将一组数字、字母或符号进行排列,以得到不同的组合顺序,例如1 2 3这三个数的全排列有:1 2 3、1 3 2、2 1 3、2 3 1、3 1 2、3 2 1。

题目解析:

设一组数p = {r1, r2, r3, … ,rn}, 全排列为perm(p),pn = p – {rn}。 则perm(p) = r1perm(p1), r2perm(p2), r3perm(p3), … , rnperm(pn)。当n = 1时perm(p} = r1。 如:求{1, 2, 3, 4, 5}的全排列 1、首先看最后两个数4, 5。 它们的全排列为4 5和5 4, 即以4开头的5的全排列和以5开头的4的全排列。 由于一个数的全排列就是其本身,从而得到以上结果。 2、再看后三个数3, 4, 5。它们的全排列为3 4 5、3 5 4、 4 3 5、 4 5 3、 5 3 4、 5 4 3 六组数。 即以3开头的和4,5的全排列的组合、以4开头的和3,5的全排列的组合和以5开头的和3,4的全排列的组合。

程序代码:

#include <gtest/gtest.h>
using namespace std;

// 全排列

void Swap(int* v1, int* v2)
{
if (v1 == v2)
return;

int value = *v1;
*v1 = *v2;
*v2 = value;
}

void ShowResult(int data[], int size, int count)
{
for (int i = 0; i < size; ++i)
{
cout << data[i] << " ";
}

if (count % 8 == 0)
{
cout << endl;
}
else
{
cout << "  ";
}
}

void Permutation(int data[], int begin, int end, int& count)
{
if (begin < end)
{
for (int i = begin; i < end; ++i)
{
Swap(&data[begin], &data[i]);
Permutation(data, begin+1, end, count);
Swap(&data[begin], &data[i]);
}
}
else
{
++count;
ShowResult(data, end ,count);
}
}

TEST(Algo, tPermutation)
{
int data[] = {1,2,3,4};
int nCount = 0;

// 4个数 4! = 24
Permutation(data, 0, 4, nCount);
ASSERT_EQ(nCount, 24);

// 5个数 5! = 120
int data1[] = {1,2,3,4,5};
nCount = 0;
Permutation(data1, 0, 5, nCount);
ASSERT_EQ(nCount, 120);

// 6个数 6! = 720
int data2[] = {1,2,3,4,5,6};
nCount = 0;
Permutation(data2, 0, 6, nCount);
ASSERT_EQ(nCount, 720);
}


参考引用:

排列及计算公式:

从n个不同元素中,任取m(m≤n)个元素按照一定的顺序排成一列,叫做从n个不同元素中取出m个元素的一个排列;从n个不同元素中取出m(m≤n)个元素的所有排列的个数,叫做从n个不同元素中取出m个元素的排列数,用符号 p(n,m)表示。

p(n,m)=n(n-1)(n-2)……(n-m+1)= n!/(n-m)!(规定0!=1)


看书、学习、写代码
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: