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<algorithm>
#include<set>
#define lol(i,n) for(int i=0;i<n;i++)
#define mod 1000000007
typedef long long ll;
using namespace std;

int main(){
    int n,m;
    while(cin>>n>>m&&n){
	set<ll> st;
	int p[1010];
	st.insert(0);
	lol(i,n){
	    cin>>p[i];
	    lol(j,i)st.insert(p[i]+p[j]);
	}
	ll ans=0;
	for(auto x:st){
	    if(x>m)continue;
	    auto it=st.upper_bound(m-x);it--;
	    ans=max(ans,*it+x);
	}
	cout<<ans<<endl;
    }
    return 0;
}

C++: #include <cstdio>
#include <algorithm>
int a[1001],b[2001],*p;main(){
	int n,m,i,j,k,r;
	for(;scanf("%d%d",&n,&m),n;printf("%d\n",r)){
		for(i=1;i<=n;i++)scanf("%d",a+i);
		for(k=i=0;i<=n;i++)for(j=i;j<=n;j++)b[k++]=a[i]+a[j];
		std::sort(b,b+k);
		for(r=i=0;i<k;i++){
			p=std::upper_bound(b,b+k,m-b[i]);
			if(p>b&&r<b[i]+*(p-1))r=b[i]+*(p-1);
		}
	}
}

C++: #include<iostream>
#include<algorithm>
#include<vector>
using namespace std;
int main(){
	while(1){
	int n,m,p,q=0,r=0,l=0,s=0,e=0,ans=0;
	cin>>n>>m;
		if(n==0 && m==0)
			break;
	vector<int> a,x;
	a.push_back(0);
	for(int i=0;i<n;i++){
		cin>>p;
		a.push_back(p);
	}
	q=n+1;
	//cout<<q<<endl;
	for(int i=0;i<q;i++){
		for(int j=0;j<q;j++){
			x.push_back(a[i]+a[j]);
		}
	}
	sort(x.begin(),x.end());
	//for(int i=0;i<q*q;i++)
	//cout<<x[i]<<' ';
	//cout<<endl;
	for(int i=0;i<x.size();i++){
		r=m-x[i];
		//cout<<r<<"を探します"<<endl;
		if(r>=0){
			s=0;
			e=q*q;
			l=(s+e)/2;
			while(s<e){
				//cout<<"l="<<l<<endl;
				l=(s+e)/2;
				if(x[l]==r)break;
				if(x[l]>r){
					e=l-1;
				}else{
					s=l+1;
				}
			}
			while(x[l]>r&&p>0)
			p--;
			while(1){
				if(l+1==q*q)break;
				if(x[l+1]<=r){l++;
				else break;
				}
			}
		}
		ans=max(ans,x[i]+x[l]);
	}
		cout<<ans<<endl;
	}
	return 0;
}

C++: //JOI 2008??´???3??? ?????????

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<iostream>
#include<cmath>

using namespace std;

#define MAX -210000000
#define MIN 210000000

int a,b;
int d[1002],c[1001*1001],hk=0,mcunt,low,high;
int x,pr=0/*,flg[200000000]*/,m,ff=0;

int main(){ 
	
	scanf("%d %d",&a,&b);
	while(a!=0 && b!=0){
		d[0]=0;
		hk=0;
		ff=0;
		pr=0;
		for(int i=1;i<=a;i++) scanf("%d",&d[i]);
		
		for(int i=0;i<=a;i++){
			for(int j=0;j<=a;j++){
				c[hk]=d[i]+d[j];
				hk++;
			}
		}
		sort(c,c+hk);									 
		for(int i=0;i<hk;i++){
			x=b-c[i];
			low=0;
			high=hk-1;
			while(low<=high){
				m=(low+high)/2;
				if(x==c[m]){
					ff=1;
					break;
				}
				if(x>c[m]) low=m+1;
				else if(x<c[m]) high=m-1;
			}
			if(ff==1){
				pr=c[i]+c[m];
				break;
			}
			if(b>c[i]+c[high] && pr<c[i]+c[high]){
				pr=c[i]+c[high];
			}
		}
		printf("%d\n",pr);
		scanf("%d %d",&a,&b);
	}
	return 0;
}

C++: #include<stdio.h>
#include<algorithm>
#include<vector>
using namespace std;
int p[1001];
vector<int> pos;
int max(int a,int b){return a>b?a:b;}
int main(){
	int n,m;
	int i,j;
	while(1){
	scanf("%d %d",&n,&m);
	if(n==0)return 0;
	pos.clear();
	p[0]=0;
	for(i=1;i<=n;i++)scanf("%d",&p[i]);
	for(i=0;i<=n;i++){
		for(j=i;j<=n;j++)pos.push_back(p[i]+p[j]);
	}
	sort(pos.begin(),pos.end());
	int ans=0;
	for(i=0;i<=n;i++){
		for(j=i;j<=n;j++){
			int best=m-p[i]-p[j];
			int x=lower_bound(pos.begin(),pos.end(),best+1)-pos.begin();
			if(x==0)continue;
			ans=max(ans,p[i]+p[j]+pos[x-1]);
		}
	}
	printf("%d\n",ans);
	}
}

C++: #include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <climits>
#include <cmath>
#include <complex>
#include <map>
#include <set>
#include <vector>
#include <stack>
#include <queue>
#include <bitset>
#include <algorithm>
#include <numeric>
#include <functional>
#include <cassert>
#include <iomanip>
using namespace std;

#define Rep(b, e, i) for(int i = b; i <= e; i++)
#define Repr(e, b, i) for(int i = e; i >= b; i--)
#define rep(n, i) Rep(0, n-1, i)
#define repr(n, i) Repr(n-1, 0, i)
#define all(v) (v).begin(), (v).end()
#define pb(v) push_back(v)
#define uniq(v) (v).erase(unique(all(v)),(v).end())
#define bitcnt(x) __builtin_popcount(x)
#define fst first
#define snd second
#define Pqaz(T) priority_queue<T,vector<T>,greater<T>>
#define Pqza(T) priority_queue<T>
#define put(x) cout << x;
#define putsp(x) cout << x << ' ';
#define putbd cout << "---------------------------------------------" << endl;
#define putln(x) cout << x << endl;
#define debug(x) cerr << #x << "=" << x << endl;
#define ENJYU std::ios::sync_with_stdio(false);std::cin.tie(0);

typedef long long ll;
typedef pair<ll, ll> llP;
typedef pair<int, int> intP;
typedef complex<double> comp;
typedef vector <int> vec;
typedef vector <ll> vecll;
typedef vector <double> vecd;
typedef vector <vec> mat;
typedef vector <vecll> matll;
typedef vector <vecd> matd;

//vector の中身を出力
template <class T>ostream &operator<<(ostream &o,const vector<T>&v)
{o<<"{";for(int i=0;i<(int)v.size();i++)o<<(i>0?", ":"")<<v[i];o<<"}";return o;}

const int MAX = 200020;
const double PI = 3.14159265358979323846;
const double EPS = 1e-12;
const int INF = 1<<29;
const ll INFL = 1e18;
const int MOD = 1000000007;

const int dx[]={1,0,-1,0},dy[]={0,1,0,-1};
//const int dx[]={-1,-1,-1,0,1,1,1,0},dy[]={-1,0,1,1,1,0,-1,-1};

//********************************template END****************************************//

void solve(void){

	int N, M;
	cin >> N >> M;
	vec ns(N);
	rep(N, i)
	{
		cin >> ns[i];
	}
	vec ss;
	ss.pb(0);
	rep(N, i)
	{
		ss.pb(ns[i]);
		Rep(i, N-1, j)
		{
			ss.pb(ns[i]+ns[j]);
		}
	}
	sort(all(ss));
	uniq(ss);
	//cout << ss << endl;

	int ans = 0;

	rep(N, i) Rep(i, N-1, j)
	{
		int tmp = ns[i]+ns[j];
		int partner = *(upper_bound(all(ss), M-tmp)-1);
		if (tmp + partner <= M)
		{
			ans = max(ans, tmp + partner);
		}
	}

	cout << ans << endl;
}

int main(void){
	solve();
	//cout << "yui(*-v・)yui" << endl;
	return 0;
}

C++: #include <iostream>
#include <vector>
#include <algorithm>

using namespace std;

int main(){

	int n,m;
	while(cin>>n>>m&&!(n==0&&m==0)){
		int scores[1001];
//		vector<int> comb;
		int comb[1000001];
		int cn=0;

		for(int i = 0; i < n; i++){
			cin>>scores[i];
		}
		scores[n]=0;
		for(int i = 0; i < n+1; i++){
			for(int j = 0; j < n+1; j++){
				int sum=scores[i]+scores[j];
				if(sum<=m){
					//comb.push_back(sum);
					comb[cn]=sum;
					cn++;
				}
			}
		}
		//sort(comb.begin(),comb.end());
		sort(comb,comb+cn);
		//comb.erase(unique(comb.begin(),comb.end()),comb.end());

		int maxNum=0;
		for(int i = 0; i < n; i++){
			for(int j = 0; j < n; j++){
				int left = (scores[i]+scores[j]);
				if(left<=m&&comb[0]+left<=m){
					//vector<int>::iterator it = lower_bound(comb.begin(),comb.end(),m-left);
					int *it = lower_bound(comb,comb+cn,m-left);
					if(it==comb+cn){
						maxNum=max(maxNum,comb[cn-1]+left);
					}
					else{
						if(*it==(m-left)){
							maxNum=m;
						}
						else{
							it--;
							maxNum=max(maxNum,*it+left);
						}
					}
				}
			}
		}
		cout<<maxNum<<endl;
	}

	return 0;
}