Go: ///
// File:  0529.go
// Author: ymiyamoto
//
// Created on Wed Feb 28 20:39:28 2018
//
package main

import (
	"fmt"
	"sort"
)

func max(n, m int64) int64 {
	if n < m {
		return m
	} else {
		return n
	}
}

func main() {
	for {
		var N int
		var M int64
		fmt.Scan(&N, &M)
		if N == 0 && M == 0 {
			break
		}

		arr := make([]int64, N+1)
		for i := 1; i <= N; i++ {
			fmt.Scan(&arr[i])
		}
		sort.Slice(arr, func(i, j int) bool { return arr[i] < arr[j] })

		sums := make([]int64, len(arr)*len(arr))
		for i := 0; i < len(arr); i++ {
			for j := 0; j < len(arr); j++ {
				sums[i*len(arr)+j] = arr[i] + arr[j]
			}
		}

		sort.Slice(sums, func(i, j int) bool { return sums[i] < sums[j] })
		var m int64 = 0
		for _, val := range sums {
			rem := M - val
			if rem >= 0 {
				index := sort.Search(len(sums), func(i int) bool { return sums[i] > rem }) - 1
				if index >= 0 {
					m = max(m, val+sums[index])
				}
			}
		}
		fmt.Println(m)
	}
}

C++: #include <iostream>
#include <string>
#include <vector>
#include <cstdlib>
#include <cstdio>
#include <cmath>
#include <algorithm>
#include <map>
#include <stack>
#include <queue>
#include <set>
#include <cstring>

using namespace std;
// ascending order
#define vsort(v) sort(v.begin(), v.end())
// descending order
#define vsort_r(v) sort(v.begin(), v.end(), greater<int>())
#define vunique(v) v.erase(unique(v.begin(), v.end()), v.end())
#define mp make_pair
#define ts(x) to_string(x)
#define rep(i, a, b) for(int i = (int)a; i < (int)b; i++)
#define repm(i, a, b) for(int i = (int)a; i > (int)b; i--)
#define bit(a) bitset<8>(a)
#define des_priority_queue priority_queue<int, vector<int>, greater<int> >
typedef long long ll;
typedef pair<int, int> P;
const ll INF = 1e18;

#define MAX_V 1000000

int main(){
	cin.tie(0);
	ios::sync_with_stdio(false);

	vector<int> rsl;
	while(true) {
		int N, M;
		cin >> N >> M;
		if(N == 0 and M == 0) break;

		vector<int> P;
		rep(i, 0, N) {
			int p;
			cin >> p;
			P.push_back(-p);
		}

		vsort(P);

		int total_point = 0;
		while(M > -P[P.size() - 1]) {
			int get_point = -1 * (*lower_bound(P.begin(), P.end(), -M));
			M -= get_point;
			total_point += get_point;
		}
		rsl.push_back(total_point);
	}

	rep(i, 0, rsl.size()) cout << rsl[i] << endl;


}

C++: //Solution for AOJ 0529: Darts 
#include <iostream>
#include <queue>
using namespace std;
const int MAX_M = 200000000;
int n, m, p[1000], save;
bool  dp[MAX_M+1];
queue <int> que;
int main() {
	while (cin >> n >> m){
		for (int i = 0; i<n; i++){
			cin >> p[i];
		}
		for(int i=0;i<m;i++){
			dp[i]=0;
		}
		dp[0] = 1;
		que.push(0);
		for (int i = 0; i<n; i++){
			dp[p[i]] = 1;
			que.push(p[i]);
		}
		for (int i = 1; i<4; i++){
			save=que.size();
			for (int k=0;k<save;k++){
				for (int j = 0; j < n; j++){
					if (que.front() + p[j] < m){
						dp[que.front() + p[j]] = 1;
						que.push(que.front() + p[j]);
					}
				}
				que.pop();
			}
		}
		for (int i = m - 1; i >= 0; i--){
			if (dp[i] != 0){
				cout << i << endl;
				break;
			}
		}
	}
	return 0;
}

C++: #include <bits/stdc++.h>
using namespace std;
int main(){
	int n,m;
	while(true){
		cin>>n>>m;
		if(n==0)	return 0;
		vector<int> p(n);
		for(int i=0;i<n;i++)	cin>>p[i];
		p.push_back(0);
		set<int> s;
		for(int i=0;i<n+1;i++){
			for(int j=0;j<n+1;j++)	s.insert(p[i]+p[j]);
		}
		int ans=0;
		for(set<int>::iterator it=s.begin();it!=s.end();it++){
			if(*it>=m)	break;
			set<int>::iterator it2=s.lower_bound(m-*it);
			if(it2!=s.begin())	it2--;
			ans=max(ans,*it+*it2);
		}
		cout<<ans<<endl;
	}
}

C++: #include <iostream>
using namespace std;

int max(int x, int y);
int add(int x, int y, int m);

int main(){
  int n, m;
  while(cin >> n >> m, n&&m){
    int dp[4][n];
    for(int i = 0; i < 4; i++){
      for(int j = 0; j < n; j++){
	dp[i][j]  = 0;
      }
    }
    for(int i = 0; i < n; i++){
      cin >> dp[0][i];
    }

    for(int i = 1; i < 4; i++){
      for(int j = 0; j < n; j++){
	dp[i][j] = dp[i-1][j];
	for(int k = 0; k < n; k++){
	  dp[i][j] = max(add(dp[i-1][j], dp[0][k], m), dp[i][j]);
	}
      }
    }
    int max = 0;
    for(int i = 0; i < n; i++){
      if(dp[3][i] > max) max = dp[3][i];
    }
    cout << max << endl;
  }
}


int max(int x, int y){
  return x < y ? y : x;
}

int add(int x, int y, int m){
  return x+y < m ? x+y : 0;
}

C++: #include <iostream>
#include <vector>
#include <string>
#include <stack>
#include <queue>
#include <deque>
#include <set>
#include <map>
#include <algorithm>	// require sort next_permutation count __gcd reverse etc.
#include <cstdlib>	// require abs exit
#include <cstdio>	// require scanf printf
#include <functional>
#include <numeric>	// require accumulate
#include <cmath>
#include <climits>
#include <limits>
#include <cfloat>
#include <iomanip>	// require setw
#include <sstream>	// require stringstream 
#include <cstring>	// require memset
#include <cctype>	// require tolower, toupper
#include <fstream>	// require freopen
#include <ctime>
#define rep(i,n) for(int i=0;i<(n);i++)
#define ALL(A) A.begin(), A.end()

using namespace std;

typedef long long ll;
typedef pair<int, int> P;

int main()
{
//	cut here before submit 
//	freopen ("testcase.darts", "r", stdin );
	int n, m;
	while (cin >> n >> m && n && m ){
		vector<int> p (n, 0 );
		rep (i, n ){
			cin >> p[i];
		} // end rep
		sort (ALL (p ), greater<int>() );
		int curr = 0, arrow = 0;
		rep (i, n ){
			while (curr <= m && arrow <= 4 ){
				curr += p[i];
				arrow++;
			} // end while
			while (curr > m ){
				curr -= p[i];
				arrow--;
			} // end while
		} // end rep
		cout << curr << endl;
	} // end loop
		
	return 0;
}

C++: #include <vector>
#include <list>
#include <map>
#include <set>
#include <deque>
#include <stack>
#include <bitset>
#include <algorithm>
#include <functional>
#include <numeric>
#include <utility>
#include <sstream>
#include <iostream>
#include <iomanip>
#include <cstdio>
#include <cmath>
#include <cstdlib>
#include <cctype>
#include <string>
#include <cstring>
#include <ctime>
#include <fstream>
#include <queue>

#define INF 100000000
#define EPS 1e-9

using namespace std;

typedef long long ll;

#define MAX_N 1000
ll N, M;
ll P[MAX_N+1];

vector<ll> ans_list;

int main(){

	while (true){
		vector<ll> date;
		cin >> N >> M;
		if (N == 0 && M == 0)
			break;
		P[0] = 0;
		for (int i = 1; i <= N; i++){
			cin >> P[i];
		}

		for (int i = 0; i <= N; i++){
			for (int j = i; j <= N; j++){
				date.push_back(P[i] + P[j]);
			}
		}

		sort(date.begin(), date.end());
		
		ll ans = 0;

		for (int num = 0; num < date.size(); num++){
			int lb = 0, ub = date.size();
			if (M < date[num])
				break;
			while (ub - lb > 1){
				int mid = (ub + lb) / 2;
				if (date[mid] > M - date[num])
					ub = mid;
				else
					lb = mid;
			}
			
			ans = max(ans, date[lb] + date[num]);
		}

		ans_list.push_back(ans);

	}

	for (int i = 0; i < ans_list.size(); i++){
		cout << ans_list[i] << endl;
	}

	return 0;

}

C++: #include <iostream>
#include <set>
#include <algorithm>
using namespace std;

set<long long> sep,sem;
long long ary[1010];
int main(){
	int N;
	long long M,hog,res;
	set<long long>::iterator it,it2;
	while(1){
		sep.clear();
		sem.clear();
		cin>>N>>M;
		if(N==0&&M==0) break;
		for(int i=0;i<N;i++){
			cin>>ary[i];
		}
		ary[N]=0;
		for(int i=0;i<=N;i++){
			for(int j=i;j<=N;j++){
				if(ary[i]+ary[j]<=M){
					sep.insert(ary[i]+ary[j]);
					sem.insert(-ary[i]-ary[j]);
				}
			}
		}
		res=0;
		for(it=sep.begin();it!=sep.end();it++){
			hog=(*it)-M;
			it2=lower_bound(sem.begin(),sem.end(),hog);
			res=max(res,(*it)-(*it2));
		}
		cout<<res<<endl;

	}
	return 0;
}