计算N个整数组合的绝对值
Compute Absolute values of N integer combinations Combinations
对于N个数(a..N),我正在用以下方法寻找所有组合的集合:
void create_print_combinations(int *t, int x, int n) {
if(x == 0) {
char p [2 * r + 2];
memset (p, 0, 2 * r +2);
for (int j=c;j>0;j--)
if(j == c)
sprintf(p, "%d", t[j]);
else
sprintf(p, "%s,%d", p,t[j]);
print_combi(p);
} else {
for (int i= n; i < r; i++) {
t[x] = a[i];
create_print_combinations(t, x-1, i+1);
}
}
}
调用函数如下:
int main() {
unsigned long int start=0, end=0;
printf ("nEnter the a positive integer N:");
scanf("%d", &r);
start=time(NULL);
a = new int[r];
for (int i = 0;i<r;i++)
a[i]=i+1;
for(int j=1;j<=r;j++) {
a1 = new int[j];
c=j;
create_print_combinations(a1, c, 0);
delete[] a1;
}
end=time(NULL);
printf("Total time taken = %llun" , end - start);
return 0;
}
给出如下组合:
输入正整数N:4
Combo : [1]
Combo : [2]
Combo : [3]
Combo : [4]
Combo : [1,2]
Combo : [1,3]
Combo : [1,4]
Combo : [2,3]
Combo : [2,4]
Combo : [3,4]
Combo : [1,2,3]
Combo : [1,2,4]
Combo : [1,3,4]
Combo : [2,3,4]
Combo : [1,2,3,4]
现在我的任务是查找所有组合的绝对值,例如:
对于Combo[1,2,3,4],应该是:
1+2+3+4 = abs(1+2+3+4)
1+2+3-4 = abs(1+2+3-4)
1+2-3-4 = ..
1-2-3+4 = ...
等等
我正在尝试以下逻辑:
while(pos > 0)
{
for(int a=0; a < i; a++)
{
if(a==0)
sprintf(p,"%d", t[a]);
else if(a == pos)
sprintf(p,"%s%c%d",p, minus, t[a]);
else
sprintf(p,"%s%c%d",p, plus, t[a]);
}
print(p);
memset (p , 0, 2 * r +2);
pos --;
}
但是我认为我做错了什么,因为所有的集合都没有打印出来。虽然我觉得快要完成了,但我还是不能把逻辑框定下来。下面是我的整个程序:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include <time.h>
int *a;
int *a1;
int r;
int c;
unsigned long int no =1;
int stoi(char *var)
{
int n1 = 0;
int n2 = 0;
int n3 = 0;
char sign=0;
while(*var)
{
if(isspace(*var))
{
var++;
continue;
}
while(*var >= '0' && *var <= '9')
{
n1=(n1*10) + (*var - '0');
var++;
continue;
}
if(sign == '+')
{
n2=n2+n1;
n1=0;
}
else if(sign == '-')
{
n2=n2 - n1;
n1=0;
}
if(*var == '+' || *var == '-')
{
if(sign == 0)
{
n2=n1;
n1=0;
}
sign = *var;
}
var++;
}
if(sign == 0)
return abs(n1);
return abs(n2);
}
void print(char* var)
{
printf("[Combo %llu.] %s = %dn" , no++, var, stoi(var));
}
void print_combi(char * a)
{
int t[c];
char *x = NULL;
char *y = a;
int i=0;
while((x=strchr(y, ',')) != NULL)
{
*x = ' ';
t[i++]=atoi(y);
y=x+1;
}
t[i++]=atoi(y);
int count =0;
int loop = 0;
char p [2 * r + 2];
memset (p , 0, 2 * r +2);
char plus = '+';
char minus = '-';
for(int k=0;k<2;k++)
{
if(k==1)
{
plus = '-';
minus = '+';
}
if(i>1)
{
for(int a=0; a < i; a++)
{
if(a==0)
sprintf(p,"%d", t[a]);
else
sprintf(p,"%s%c%d",p, plus, t[a]);
}
}
else if(i==1)
{
sprintf(p,"%d", t[i-1]);
print(p);
break;
}
print(p);
memset (p , 0, 2 * r +2);
if(i==2)
continue;
if(i==3 && k ==1)
break;
int pos = i-1;
while(pos > 0)
{
for(int a=0; a < i; a++)
{
if(a==0)
sprintf(p,"%d", t[a]);
else if(a == pos)
sprintf(p,"%s%c%d",p, minus, t[a]);
else
sprintf(p,"%s%c%d",p, plus, t[a]);
}
print(p);
memset (p , 0, 2 * r +2);
pos --;
}
}
}
void create_print_combinations(int *t, int x, int n)
{
if(x == 0)
{
char p [2 * r + 2];
memset (p, 0, 2 * r +2);
for (int j=c;j>0;j--)
if(j == c)
sprintf(p, "%d", t[j]);
else
sprintf(p, "%s,%d", p,t[j]);
print_combi(p);
}
else
for (int i= n; i < r; i++)
{
t[x] = a[i];
create_print_combinations(t, x-1, i+1);
}
}
int main()
{
unsigned long int start=0, end=0;
printf ("nEnter the a positive integer N:");
scanf("%d", &r);
start=time(NULL);
a = new int[r];
for (int i = 0;i<r;i++)
a[i]=i+1;
for(int j=1;j<=r;j++)
{
a1 = new int[j];
c=j;
create_print_combinations(a1, c, 0);
delete[] a1;
}
end=time(NULL);
printf("Total time taken = %llun" , end - start);
return 0;
}
根据程序逻辑,我正在将组合计算为字符串并生成表达式的绝对值。
有一种更简单的方法。你想要加一个N个整数的向量:
[1*k1, 2*k2, 3*k3,…]N * kN)
where kx = - 1,0, +1
对于x=1..N, kx有3^N种组合
@ steve的解决方案:
#include <iostream>
#include <sstream>
using namespace std;
void print_sum(int N, int sum_so_far, string as_a_string) {
if(N) {
ostringstream oss; oss << N;
print_sum(N-1, sum_so_far+N, as_a_string + "+" + oss.str() + " ");
print_sum(N-1, sum_so_far-N, as_a_string + "-" + oss.str() + " ");
print_sum(N-1, sum_so_far, as_a_string);
} else {
if (sum_so_far < 0) sum_so_far *= -1;
cout << as_a_string << "t= " << sum_so_far << endl; }
}
int main() {
print_sum(4, 0, "");
}
输出开始:
+4 +3 +2 +1 = 10
+4 +3 +2 -1 = 8
+4 +3 +2 = 9
+4 +3 -2 +1 = 6
+4 +3 -2 -1 = 4
+4 +3 -2 = 5
+4 +3 +1 = 8
+4 +3 -1 = 6
# .. and so on
你要做的是非常类似于枚举从"N选1"到"N选N"的所有组合。我建议你用google搜索"枚举组合"
这是我找到的一个链接:
http://www.codeproject.com/KB/recipes/CombC.aspx下面是如何做到这一点的逻辑。打印大小为n-1
的所有二进制数字,其中n
是各自组合的大小(元素数)。例如,要为组合[1,2,3,4]做你想做的事情,创建3
的所有二进制组合(n-1 = 3,这里n = 4个元素)。例如
when n = 3, the possible combinations are:
000
001
010
011
100
101
110
111
现在在for循环中运行你的组合,每当你发现0
时,就在里面做加法,每当你发现1
时,就做减法。例如,000
表示1+2+3+4
, 101
表示1-2+3-4
。
相关文章:
- 如何在OMNET++中指定与命令行参数组合的输出文件名
- 仅使用绝对值对数组进行排序,并在C++中显示实际值
- 可组合的lambda/std::函数与std::可选
- 如何将两个不同矢量的同一位置的两个元素组合在一起
- 混合组合和继承的C++问题
- 我需要将多个函数组合为一个函数
- 构建可组合有向图(扫描仪生成器的汤普森构造算法)
- 通过组合不同的类型来创建唯一的id
- 用常见虚拟函数实现的任意组合来实现派生类的正确方法是什么
- 模板元编程:如何将参数包组合成新的参数包
- 检查向量是否具有所有可能的字符组合
- 如何在加密++中将两个源组合成新的源
- 根中的组合
- 更改 C++ 中的组合分类变量
- 错误:(-210:不支持的格式或格式组合)功能'create'中的硬件视频解码器不支持视频源
- 线性优化目标函数中的绝对值
- 组合字符串不适用于 libCurl,C++
- 测试两个类型列表中的所有组合
- 将多个 for 循环组合成单个迭代器
- 计算N个整数组合的绝对值