C 从长度为k的n个数中生成递增子序列

C 从长度为k的n个数中生成递增子序列,c,arrays,loops,recursion,subsequence,C,Arrays,Loops,Recursion,Subsequence,我想生成从1到n的所有可能递增的数字子序列(允许重复),但长度为k。 例:n=3,k=2 输出: 1 1 1 2 1 3 2 2 2 3 3 3 这是我的代码: #include <stdio.h> int s[100]; int n=6; int k=4; void subk(int prev,int index) { int i; if (index==k) { for(int i=0; i<k; i++)

我想生成从1到n的所有可能递增的数字子序列(允许重复),但长度为k。
例:n=3,k=2
输出:

1 1
1 2
1 3
2 2
2 3
3 3
这是我的代码:

#include <stdio.h>

int s[100];
int n=6;
int k=4;

void subk(int prev,int index)
{
    int i;
    if (index==k)
    {
        for(int i=0; i<k; i++)
            printf("%d ",s[i]);

        printf("\n");
        return;
    }
    s[index]=prev;
    for (i=prev; i<=n; ++i)
    {
        subk(i,index+1);//,s,n,k);
    }

}
int main()
{
    int j;
    for (j = 1; j<=n ; ++j)
    {
        subk(j,0);
    }
    return 0;
}    
#包括
int s[100];
int n=6;
int k=4;
无效子k(整数上一个,整数索引)
{
int i;
如果(索引==k)
{

对于(int i=0;i我已使用
n=3
k=2
测试了您的代码,并得到以下结果:

1 1
1 1
1 1
1 2
1 2
1 3
2 2
2 2
2 3
3 3
这显然是不正确的,因为有几个相同的数字,如
11
12

    correct      program (incorrect)
    k = 3        k = 2
    1 1 1        1 1     
    1 1 2        1 1     
    1 1 3        1 1     
    1 2 2        1 2     
    1 2 3        1 2     
    1 3 3        1 3     
    2 2 2        2 2     
    2 2 3        2 2     
    2 3 3        2 3     
    3 3 3        3 3     
但到底出了什么问题?
如果
n=3
k=3
,让我们写下正确的结果。现在将这些结果与我们在
n=3
k=2
时从程序得到的结果进行比较

    correct      program (incorrect)
    k = 3        k = 2
    1 1 1        1 1     
    1 1 2        1 1     
    1 1 3        1 1     
    1 2 2        1 2     
    1 2 3        1 2     
    1 3 3        1 3     
    2 2 2        2 2     
    2 2 3        2 2     
    2 3 3        2 3     
    3 3 3        3 3     
现在我们可以看到,当我们设置
k=3
时,程序的错误输出与正确答案的前两列相同。这意味着如果我们设置
k=2
,程序解决了3列的问题,但只显示前两列

您需要停止程序多次写入相同的数字

解决方案1 一种方法是,当subk函数将最后一个数字(
index==(k-1)
)写入缓冲区
s
时,只在subk函数中执行一次for循环。 为了实现这一点,您需要将以下两行添加到for循环的末尾

if (index == (k - 1))
    break;
(也可以使用return代替break)

添加这两行后,函数应如下所示:

void subk(int prev, int index)
{
    int i;
    if (index == k)
    {
        for (int i = 0; i<k; i++)
            printf("%d ", s[i]);

        printf("\n");
        return;
    }
    s[index] = prev;
    for (i = prev; i <= n; ++i)
    {
        subk(i, index + 1);//,s,n,k);
        if (index + 1 == k)
            break;
    }

}
使用此解决方案,当
索引
显示程序位于最后一个“子编号”时,不会执行for循环。它只显示编号,并由于返回而退出函数


两种解决方案都得到了正确的结果,但我个人更喜欢第二种解决方案,因为for循环的每次迭代都不会执行额外的if语句,而且程序(稍微)更快。

为什么在if条件下使用return语句???
int s[100];
全局声明
int s[4];
main()
中。为什么?@Vijayraj S(1,1)、(2,2)和(3,3)没有增加子序列。@vladfrommosco,但我确实需要这些子序列作为well@AditiRawat对不起,谢谢你指出