引用:
int a,b,c,d,......
int sum
=>
定義一類或一組變量
數組
1.數組是什么?
數組是一組具有相同類型的數據(變量)的集合
C語言中數組:
一維數組
二維數組
三維數組
...
其實,C語言中只有一維數組
2,一維數組
2.1 定義格式
類型說明符 數組名[整型表達式] {={初始化列表}};
{}: 可要可不要
"類型說明符":指定數組元素的類型,任意C語言合法的類型都可以
“數組名”:對象的名字,命名要符合C語言標識符的規定
“整型表達式” :指定數組中元素的個數,一般為常量表達式
eg:
#define N 3
int a[10];//定義了一個數組,數組名a,里面有10個int型元素
typeof(a) =>一個具有10個int元素的數組類型 int[10]
char b[10];
typeof(b) => 一個具有10個char元素的數組類型 char[10]
int c;//在程序運行的時候,為c分配4個字節的空間
在程序運行的時候,為a分配多大的空間?
10個int =》40個字節
sizeof(a) =>40
2.2 一維數組在內存中的存放
在連續的地址空間中,從低地址到高地址依次存放數組中的每個元素。
意思:第二個元素只能緊跟着第一個元素后面存放
int a[10];
0x0001 -> 第一個元素
0x0005 -> 第二個元素
....
2.3一維數組元素的引用
int a[10];
引用方式:
數組名[下標];//C語言的下標是從0開始
a[0] 數組中第一個元素
...
a[9]
引用數組元素a[i] 和引用普通變量是一樣的,都有左值和右值,還可以取地址
eg:
int b;
b = 1024;
a[0] = 1024;//表示數組元素a[0]的地址
b = a[0]; //表示數組元素a[0]的值
練習:
定義一個整型數組,數組中有10個元素。從鍵盤上輸入值來給元素賦值
然后把整個數組輸出
int a[10];
for(i = 0; i<10;i++)
{
scanf("%d",&a[i]);
}
printf("%d\n",a);
2.4 一維數組的初始化
初值是存在一對花括號中
(1)數組元素全部初始化
int a[10] = {1,2,3,4,5,6,7,8,9,10};
eg:
int a[10];
a[10] = {1,2,3,4,5,6,7,8,9,10};//error
(2)可以只對部分元素初始化,后面的元素自動初始化為0
int a[10] = {1,2,3};
把整個數組初始化為0
int a[10] = {0};
(3)如果對全部元素初始化,那么在定義數組的時候,可以不指定數組的長度
why?
int a[] = {1,2,3};
☆☆
char s[] = {'a','b','c'};
=>數組s里面有3個元素
printf("%s",s);
char s1[10] = {'a','b','c'};
printf("%s",s1);
“字符串長度” :就是從一個起始地址的內容開始找,找到第一個\0為止
前面有多少個字符,那就是字符串的長度
數組的長度 :數組有多少個元素
eg:
int a[10];
sizeof(a)/sizeof(a[0])
字符數組的大小:這個數組所占空間的大小
sizeof(s) => 3
sizeof(s1) => 10
練習:
(1)求一個一維數組(int)中元素之和
最大值,最小值 3.c
"遍歷" :對某個對象中每個元素訪問且僅訪問一次
int x,i,max,min,sum;
scanf("%d",&x);
int a[x];
max = a[0];
min = a[0];
for(i = 0;i <x;i++)
{
scanf("%d",&a[i]);
}
for(i = 0; i < x;i++)
{
if(max < a[i])
{
max = a[i];
}
if(min > a[i])
{
min = a[i];
}
}
printf("max = %d,min = %d\n",max,min);
(2)Fibonacci(斐波那契數列前20項之和)
1 1 2 3 5 8 13 21 ...
從第三項開始,每一項都是前面兩項之和
int Fi[20] = {1,1};
int sum = 2;
Fi[2] = Fi[1] +Fi[0];
sum += Fi[2];
Fi[3] = Fi[2] +Fi[1];
sum += Fi[3];
...
for(i = 2;i < 20;i++)
{
Fi[i] = Fi[i-1] +Fi[i-2];
sum += Fi[i];
}
(3)給定一個一維數組(int),判斷是否為遞增數組
a[0] < a[1] <a[2] <a[3]...a[n-1]
int x,i;
scanf("%d",&x);
int a[x];
int flag = 1;//遞增標志位 1 :遞增 ,0 :非遞增
for(i = 0;i <x;i++)
{
scanf("%d",&a[i]);
}
for(i = 0;i < x-1;i++)
{
if(a[i] >= a[i+1] )
{
flag = 0;
break;
}
}
/*
if(i == x-1)
{
printf("yes\n");
}
*/
if(flag)
{
printf("yes\n");
}
(4)在一個給定的升序的一維數組中,查找一個元素
int a[10];
查找數組a中是否有元素x,有就打印yes,沒有就打印no
二分法/二分查找法
代碼
int find(int n,int a[],int l)
{
int low=0;
int high=l-1;
int middle=0;
while(low<high)
{
middle=(low+high)>>1;
if(n==a[middle])
{
printf("%d,%d",n,middle);
return 1;
}
else if(n>a[middle])
low=middle+1;
else
high=middle-1;
}
return 0;
}
int main()
{
int a[]={2,3,5,6,7,8,9,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60};
int l=sizeof(a)/sizeof(a[0]);
int i=0,n;
printf("arry content");
for(i=0;i<l;i++)
{
if(i%8==0)
printf("\n");
printf("%4d",a[i]);
}
printf("\nseach n is ");
scanf("%d",&n);
if(!find(n,a,l))
printf("not fond");
return 0;
}
二分查找的基本思想是:(設R[low..high]是當前的查找區間)
(1)首先確定該區間的中點位置:
(2)然后將待查的K值與R[mid].key比較:若相等,則查找成功並返回此位置,否則須確定新的查找區間,繼續二分查找,具體方法如下:
①若R[mid].key>K,則由表的有序性可知R[mid..n].keys均大於K,因此若表中存在關鍵字等於K的結點,則該結點必定是在位置mid左邊的子表R[1..mid-1]中,故新的查找區間是左子表R[1..mid-1]。
②類似地,若R[mid].key<K,則要查找的K必在mid的右子表R[mid+1..n]中,即新的查找區間是右子表R[mid+1..n]。下一次查找是針對新的查找區間進行的。
因此,從初始的查找區間R[1..n]開始,每經過一次與當前查找區間的中點位置上的結點關鍵字的比較,就可確定查找是否成功,不成功則當前的查找區間就縮小一半。這一過程重復直至找到關鍵字為K的結點,或者直至當前的查找區間為空(即查找失敗)時為止。
二分查找算法
int BinSearch(SeqList R,KeyType K)
{ //在有序表R[1..n]中進行二分查找,成功時返回結點的位置,失敗時返回零
int low=1,high=n,mid; //置當前查找區間上、下界的初值
while(low<=high){ //當前查找區間R[low..high]非空
mid=(low+high)/2;
if(R[mid].key==K) return mid; //查找成功返回
if(R[mid].kdy>K)
high=mid-1; //繼續在R[low..mid-1]中查找
else
low=mid+1; //繼續在R[mid+1..high]中查找
}
return 0; //當low>high時表示查找區間為空,查找失敗
} //BinSeareh
二分查找的優點和缺點
雖然二分查找的效率高,但是要將表按關鍵字排序。而排序本身是一種很費時的運算。既使采用高效率的排序方法也要花費O(nlgn)的時間。
二分查找只適用順序存儲結構。為保持表的有序性,在順序結構里插入和刪除都必須移動大量的結點。因此,二分查找特別適用於那種一經建立就很少改動、而又經常需要查找的線性表。
對那些查找少而又經常需要改動的線性表,可采用鏈表作存儲結構,進行順序查找。鏈表上無法實現二分查找。
a:1 2 3 5 6 8 9 x = 4
l = 0
r = 6
mid = 3
=>
l = 0
r = mid-1 = 2
mid = 1
=>l = mid+1 = 2
r = 2
mid = 2
=>l = mid+1 = 3
r = 2
int a[n];
int l = 0,r = n-1;
while(l <= r)
{
mid = (l+r)/2;//范圍[l,r]中間元素的下標
if(a[mid] == x)
{
break;
}
else if(a[mid] > x)
{
r = mid-1;
}
else
{
l = mid+1;
}
}
作業:
因式分解
90 = 2*3*3*5
15
(1)將一個一維數組(int)排序
(2)一個一維數組中有正有負,寫一個程序,把數組中負數放在正數的前面
(3)求一個一維數組中第二大的元素
考慮有重復的元素
(4)一維數組的插入排序
答案
作業:
(0)因式分解
90 = 2*3*3*5
15
算法1:
sum=1;
num1 = num;
for(i=2;i<num;)
{
if(num%i==0)
{
sum*=i;
a[x]=i;
x++;
num/=i;
}
else
i++;
if(sum==num1)
break;
}
算法2:
90
[2,n/2]
for(i = 2;i <= n/2;i++)
{
while(n%i == 0)
{
printf("%d*",i);
n /= i;
}
}
printf("%d\n",n);
90
(1)將一個一維數組(int)排序
冒泡排序:
兩兩比較,大的往后移
9 7 8 4 2
7 9 8 4 2
7 8 9 4 2
7 8 4 9 2
7 8 4 2 9
if(a[0] > a[1])
{
a[0] <-> a[1]
}
if(a[1] > a[2])
{
a[1] <-> a[2]
}
...
if(a[i] > a[i+1])
{
a[i] <-> a[i+1]
}
for(i = 0;i < N-1;i++)
{
if(a[i] > a[i+1])
{
a[i] <-> a[i+1]
}
}//一趟冒泡
for(j = 0;j < N;j++)
{
for(i = 0;i < N-j;i++)
{
if(a[i] > a[i+1])
{
a[i] <-> a[i+1]
}
}
}
選擇排序:
從待排序的數組中,選擇最大的那個元素與最后面的那個元素進行交換
4 8 2 6 3
i = 0;
if(a[1] < a[0])
{
a[1] <-> a[0]
}
if(a[2] < a[0])
{
a[1] <-> a[0]
}
if(a[N-1] < a[0])
{
a[1] <-> a[0]
}
====
for(i = 0;i < N;i++)
{
for(j = i+1;j < N;j++)
{
if(a[j] < a[i])
{
a[1] <-> a[0]
}
}
}
===========
(2)一個一維數組中有正有負,寫一個程序,把數組中負數放在正數的前面
-3 4 9 -2 -3
=>
int next = 0;
for(i = 0;i < N;i++)
{
if(a[i] < 0)
{
a[next] <->a[i]
next++;
}
}
(3)求一個一維數組中第二大的元素
考慮有重復的元素
9 9 8 8 8
max = a[0];
second = [1];
for(i =0;i < M;i++)
{
if(a[i] > max)
{
second = max;
max = a[i];
}
}
(4)一維數組的插入排序二分法
int a[10];
int l,r,mid;
for(i = 0;i < 10;i++)
{
scanf("%d",&a[i]);
//排序
//找插入位置
//二分法/二分查找法
l = 0;
r = i;
while(l <= r)
{
mid = (l+r)/2;
if(a[mid] == a[i])
{
break;
}
else if(a[mid] < a[i])
{
l = mid+1;
}
else
{
r = mid-1;
}
}
//插入操作
//把插入位置及后面的元素,每一個都往后移
x = a[i];
//mid,...i-1
for(j = i-1;j >= mid;j--)
{
a[j+1] = a[j];
}
a[mid] = x;
}
7 5 6 3 2 4
5 6 7
mid i-1 i
回顧:
一維數組
定義:
數據元素的類型 數組名[數組元素個數];
int a[4];
數組a中有4個元素 a[0] a[1] a[2] a[3] ,每個元素int 型
typeof(a) =>int[4]
=>假如我們要定義3個像a這種類型的對象
對象 =》數組
typeof(a) b[3];
=>b數組名,它里面有3個元素,分別是b[0],b[1],b[2]
並且這三個元素都是typeof(a)
typeof(a) =>int[4]
int[4] b[3];
b[0] _ _ _ _
b[1] _ _ _ _
b[2] _ _ _ _
每個元素代表着一個一維數組,且每個里面有4個int
int[4] b[3]; //關鍵字不能與[]在一塊
int b[3][4];
二維數組實際上是一個一維數組,只不過該一維數組中的元素又是一個一維數組
1.二維數組
1.1二維數組的實質
是一個一維數組
1.2 二維數組的定義
類型說明符 數組名[常量表達式(行大小)][常量表達式(列大小)];
1.3 二維數組在內存中的存放
int a[3][4];
sizeof(a) => 3*4*4
按行存放,即先存放第一行的元素,在放第二行的元素
1.4 二維數組的引用
數組名[行下標][列下標]
下標:從0開始
1.5 二維數組的初始化
(1)分行給二維數組賦初值
int b[3][4];
typeof(b) =>int[4][3]
int b[3][4] = {
{1,2,3,4},//b[0]
{2,3,4,5},//b[1]
{3,4,5,6}//b[2]
};
(2)將所有數據寫在一個花括號內,按數組排列順序對各元素賦初值
int b[3][4] = {1,2,3,4,5,6,7,8,9,10,11,12};
(3)對部分元素賦初值,其余元素自動置0
int b[3][4] = {{1},{2,3},{4,5}};
or
int b[3][4] = {1,2,3,4};
(4)如果對全部元素賦初值,則定義數組時對第一維的長度省略,但第二維的長度不可以
int [][4] = {1,2,3,4,5,6,7,8};
2.字符數組
元素都是字符形式
字符串的結束標志 '\0'
char s[] = {'a','b','c','\0'};
%s :格式符 輸出字符串
遇到第一個\0結束
printf("%s\n",s);
字符串的操作函數:
strlen :求字符串的長度,
遇到第一個\0結束
strlen("gvjh") =>4
strcmp :字符串的比較函數
strcmp(s1 ,s2)
s1 > s2 return 1
s1 == s2 return 0
s < s2 return -1
strcat :字符串連接函數
s1 : "1234"
s2 : "asdf"
strcat(s1,s2);
=>1234asdf
strcpy :字符串拷貝
s1 : "1234"
s2 : "asdf"
strcpy(s1,s2);
=>asdf
練習:
(1)定義一個整型二維數組,從鍵盤上給各個元素賦值
在把整個數組輸出
(2)求一個二維數組的最大值,最小值,及所有元素的和
(3)求一個二維數組中列元素之和最大的那個列
int a[3][4]
(1)構造一個一維數組b[4],用來保存目標二維數組每一列的元素之和
int b[4] = {0};
b[0] += a[0][0]
for(i = 0;i < 4;i++)//列下標
{
for(j = 0;j < 3;j++)//行下標
{
b[i] += a[j][i]
}
}
int max = b[0];
int i_max ;
for(i = 0;i < 4;i++)
{
if(max < b[i])
{
max = b[i];
i_max = i;
}
}
(4)求一個二維數組山頂元素的個數,打印出山頂元素是哪個及其它的位置
判斷a[i][j]是否為山頂元素,實際上就是判斷比上,下,左,右都大
1 2 3 5
4 5 2 4
1 2 3 5
2 5 6 3
上 :不存在 ,存在 (比它大)
下 :不存在 ,存在 (比它大)
左 :不存在 ,存在 (比它大)
右 :不存在 ,存在 (比它大)
if(上::不存在 ,存在 (比它大)&&下 :不存在 ,存在 (比它大) && 左 :不存在 ,存在 (比它大)
&& 右 :不存在 ,存在 (比它大))
{
}
=》
int a[4][4]
if((i==0 || a[i][j] > a[i-1][j]) &&
(i == 3 || a[i][j]>a[i+1][j]) &&
(j==0 || a[i][j] > a[i][j-1]) &&
(j == 3 || a[i][j] > a[i][j+1]))
{
printf("a[%d][%d] = %d\n",i,j,a[i][j]);
}
//第四題,求一個二維數組中山頂元素的個數,也就是比四周的元素都大
//未知行列
//第三題,求一個二維數組中列元素之和的最大那個列
/* int a[3][3];
int i = 0, j;
for(i = 0; i < 3; i++)
for(j = 0; j < 3; j++)
{
scanf("%d", &a[i][j]);
}
int b[3] = {0};
for(j = 0; j < 3; j++)
{
for(i = 0; i < 3; i++)
{
b[j] += a[i][j];
}
}
if(b[0] >= b[1] && b[0] >= b[2])
{
printf("1\n");
}
if(b[1] >= b[2] && b[1] >= b[0] )
{
printf("2\n");
}
else
{
printf("3\n");
} */
//第一題,定義一個整型的二維數組,從鍵盤上給各個元素賦值,再把整個數組輸出
/*int a[3][3];
int i = 0, j;
for(i = 0; i < 3; i++)
for(j = 0; j < 3; j++)
{
scanf("%d", &a[i][j]);
}
for(i = 0; i < 3; i++)
for(j = 0; j < 3; j++)
{
printf("%d\n", a[i][j]);
}*/
//第二題,求一個二維數組的max, min, sum
/* int a[2][2];
int i, j, sum = 0, min = 0, max = 0;
for(i = 0; i < 2; i++)
for(j = 0; j < 2; j++)
{
scanf("%d", &a[i][j]);
}
for(i = 0; i < 2; i++)
for(j = 0; j < 2; j++)
{
sum += a[i][j];
if(a[i][j] <= min)
{
min = a[i][j];
}
if(a[i][j] >= max)
{
max = a[i][j];
}
}
printf("%d,%d, %d\n", min, max, sum); */
作業:
1打印楊輝三角前10行
1
1 1
1 2 1
1 3 3 1
1 4 6 4 1
1 5 10 10 5 1
2高數巨占座位
a[6][6];
n = 3
0 0 0 1 1 0
0 0 0 1 1 0
0 1 0 1 0 1
0 0 0 0 0 0
0 1 1 0 1 0
0 1 0 1 0 0
求有多少種方式
3.求一個一維數組最大子數組之和
子數組:在一個數組中下標連續的n個元素(n>0),稱為原數組的子數組
2 -1 3
2 =>2
2 -1 => 1
2 -1 3 =>4
-1 =>-1
-1 3 =>2
3 =>3
4.數組部分和
int a[N];
K
能不能從數組a中,任意選M個元素(M > 0,M <= N),使得這M個元素和為K,元素不要求連續
a:2 5 6 3 1 -1 -2 2
M = 3 (自己輸)
K = 6 (自己輸)
自己做的
第一題
#include<stdio.h>
int main()
{
printf("漢字測試:\t You know the test begin:\n");
//
//楊輝三角前10行
// 1
// 11
// 121
// 1331
// 14641
int s[10][10] = {{1},{1,1}};
int i, j;
for(i = 0; i < 10; i++)
for(j = 0; j < 10; j++)
{
if(j == 0 || i == j)
{
s[i][j] = 1;
}
else
{
s[i][j] = s[i-1][j] + s[i-1][j-1];
}
printf("%d\t", s[i][j]);
if(i == j)
{
printf("\n");
break;
}
}
return 0;
}
/* if(j == 0)//就是首直接設置
{
s[i][j] = 1;
printf("%d\t", s[i][j]);
}
if(j == i)//就是尾直接設置
{
s[i][j] = 1;
printf("%d\n", s[i][j]);
break;
}
//其余位置
s[i][j] = s[i-1][j] + s[i-1][j-1];
printf("%d\t", s[i][j]);*/
第二題
#include<stdio.h>
int main()
{
// 1.高數巨占座位
// a[6][6];
// n = 3
// 0 0 1
// 1 0 0
// 1 0 1
// 0 0 0 1 1 0
// 0 0 0 1 1 0
// 0 1 0 1 0 1
// 0 0 0 0 0 0
// 0 1 1 0 1 0
// 0 1 0 1 0 0
// 求有多少種方式
printf("漢字測試:\t You know the test begin:\n");
int i, j, o, p, n, resolution = 0, flag = 0;//op為輸入的行列
scanf("%d%d%d", &o, &p, &n);
int arg[o][p];
for(i = 0; i < o; i++)
for(j = 0; j < p; j++)
{
scanf("%d", &arg[i][j]);
}
for(i = 0; i < o; i++)
{
for(j = 0; j < p; j++)
{
if(arg[i][j] == 0)//還需要考慮一種情況,就是碰到1重置
{
flag++;
if(flag == n)
{
resolution++;
//這里更換了位置
}
}
else
{
flag = 0;//調換到這里來,才可以處理碰到1重置
}
}
flag = 0;
}
printf("這里有這么多種方案:%d\n", resolution);
return 0;
}
第三題
#include<stdio.h>
#define N 3
int main()
{
// 2.求一個一維數組最大子數組之和
// 子數組:在一個數組中下標連續的n個元素(n>0),稱為原數組的子數組
// 2 -1 3
// 2 =>2
// 2 -1 => 1
// 2 -1 3 =>4
// -1 =>-1
// -1 3 =>2
// 3 =>3
int arg[N], i, j , max = 0, sum;
for(i = 0; i < N; i++)
{
scanf("%d", &arg[i]);
}
sum = arg[0];
for(i = 0; i < N; i++)
{
max = 0;
max += arg[i];
for(j = i + 1; j < N; j++)
{
max += arg[j];
if(max > sum)
{
sum = max;
}
}
}
printf("這個最大的數為:%d\n", sum);
return 0;
}
自己第一次做的
#include<stdio.h>
int main()
{
// 2.求一個一維數組最大子數組之和
// 子數組:在一個數組中下標連續的n個元素(n>0),稱為原數組的子數組
// 2 -1 3
// 2 =>2
// 2 -1 => 1
// 2 -1 3 =>4
// -1 =>-1
// -1 3 =>2
// 3 =>3
int m, i, n, flag = 0, max = 0, j = 0;//j用來記錄第二個數組的,記錄max的大小
scanf("%d%d", &m, &n);//m是數組長度,n是n個元素
int b[m], arg[m];//b數組用來記錄連續子數組的大小
for(i = 0; i < m; i++)
{
b[i] = 0;
}
for(i = 0; i < m; i++)//輸入數組
{
scanf("%d", &arg[i]);
}
for(i = 0; i < m; i++) //從arg[0]開始往后計數
{
max += arg[i]; //累加
flag++;
if(flag == n) //標記n個就重置
{
printf("the flag is full\n");
flag = 0;
b[j++] = max; //連續記錄
max = 0;
i -= n - 1; //倒退n-1
}
}
max = b[0];
for(i = 0; i < m ; i++)
{
printf("all of the b[i] are:%d\n", b[i]);
if(b[i] >= max)
{
printf("the value of b[i] is:b[%d]\n", b[i]);
max = b[i];
}
}
printf("the maximum value is:%d\n", max);
return 0;
}
答案
作業:
1.高數巨占座位
a[6][6];
n = 3
0 0 0 1 1 0 1
0 0 0 1 1 0 1
0 1 0 1 0 1
0 0 0 0 0 0 4
0 1 1 0 1 0
0 1 0 1 0 0
int count = 0;//表示一行連續 0個數
int s = 0;//總的占座位的方式
for(i = 0;i < 6;i++)
{
count = 0;
for(j = 0;j < 6;j++)
{
if(a[i][j] == 0)
{
count++;//連續為0的個數加1
if(count >= 3)
{
s++;
}
}
else
{
count = 0;
}
}
}
printf("s = %d\n",s);
求有多少種方式
2.求一個一維數組最大子數組之和
子數組:在一個數組中下標連續的n個元素(n>0),稱為原數組的子數組
2 -1 3
2 =>2
2 -1 => 1
2 -1 3 =>4
-1 =>-1
-1 3 =>2
3 =>3
算法1:
所有的子數組
a1 所有開頭的子數組
a1
a1+a2
a1+a2+a3
j = 0;
sum = a[0];
j = 1;
sum = a[0] +a[1]
j = 2;
sum = a[0]+a[1]+a[2]
max = a[0];
sum = a[0];
for(j = 1;j < N;j++)
{
sum += a[j];
if(sum > max)
{
max = sum;
}
}
=>
max = a[0];
for(i = 0;i < N;i++)//以i開頭的子數組
{
sum = a[i];
for(j = i+1;j < N;j++)
{
sum += a[j];
if(sum > max)
{
max = sum;
}
}
}
算法2:
+ - + - - + +
sum = 0;
max = a[0];
for(i = 0;i < N;i++)
{
sum += a[i];
if(max < sum)
{
max = sum;
}
if(sum < 0)
sum = 0;
}
3.數組部分和
int a[N];
K
能不能從數組a中,任意選M個元素(M > 0,M <= N),使得這M個元素和為K,元素不要求連續
a:2 5 6 3 1 -1 -2 2
M = 3 (自己輸)
K = 6 (自己輸)
2 5 6 3 1 -1 -2 2
對於數組中的任意一個元素a[i] ,只有兩種情況
選中 1
不選 0
0 0 0 0 0 0 0 0 0 不選任意一個數組元素
1 0 0 0 0 0 0 0 1 選中a[0]
2 0 0 0 0 0 0 1 0 選中a[1]
3 0 0 0 0 0 0 1 1 選中a[0] a[1]
0 0 0 0 0 1 1 1
.....
2^n-1 1 1 1 1 1 1 1 1
(2^n -1)
0 ~2^n-1
x [0~2^n-1]
for(x = 0; x <=(1<<n)-1;x++)
{
for(j = 0;j < n;j++)
{
if(x & (1 << j))
{
//x的第jbit為1
sum += a[j];
}
}
if(sum == k)
{
}
}