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

import (
	"fmt"
	"sort"
)

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

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

		arr := make([]int, N+1)
		for i := 1; i <= N; i++ {
			fmt.Scan(&arr[i])
		}
		sort.Ints(arr)

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

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

C++: #include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <map>
#include <sstream>
#include <queue>
#include <cstdlib>
#include <algorithm>
#include <iterator>
#include <stack>
#include <list>
using namespace std;
#define INF 100000000
typedef long long int lli;
typedef pair<int,int> P;

int p[1001];
int h[1000*1000+1];

int main(){
	int n,m,ans;
	while(cin>>n>>m){
		if(n==0&&m==0) break;
		p[0]=0;
		ans=0;
		for(int i=1; i<=n; ++i){
			cin >> p[i];
		}
		for(int i=0; i<=n; ++i){	
			for(int j=0; j<=n; ++j){
				h[i*n+j]=p[i]+p[j];
			}
		}
		sort(h,h+n*n+1);
		/*
		for(int i=0; i<=n*n; ++i){
			cout << h[i] << "\n";
		}
		*/
		for(int i=0; i<=n; ++i){	
			for(int j=0; j<=n; ++j){	
				int tmp=p[i]+p[j];
				int l=0,r=n*n;
				int cnt=0;
				while(1){
					int mid=(r+l)/2;
					if(cnt>=1000){
						if(h[mid]+tmp<=m) ans=max(ans,h[mid]+tmp);
						break;
					}
					if(h[mid]+tmp>m){
						r=mid;
					} else if(h[mid]+tmp<m){
						l=mid;
					} else if(h[mid]+tmp==m){
						ans=m;
						break;
					}
					++cnt;
				}
			}
		}
		cout << ans << "\n";
	}
	return 0;
}

C++: #include<iostream>
#include<vector>
using namespace std;
typedef unsigned int uint;
uint maxv;
void solve(uint now,uint m,uint *a,int n){
  int r=n-1,l=0,mid;
  while(l <=r){
    mid = (l+r)/2;
    if ( a[mid]+now>m)r=mid-1;
    else if ( a[mid]+now <=m){
      if ( a[mid]+now >maxv)maxv=a[mid]+now;
      l=mid+1;
    }
    //else break;
  }
  //if ( now+a[mid]>maxv&& now+a[mid]<=m)maxv=now+a[mid];
}


main(){
  int n;
  uint m;
  while(scanf("%d%u",&n,&m) && n){
    uint one[n];
    uint two[n*n];
    int p=0;
    maxv=0;
    for(int i=0;i<n;i++)scanf("%u",&one[i]);
    for(int i=0;i<n;i++){
      if ( one[i]>maxv &&one[i] <=m)maxv=one[i];
      for(int j=i;j<n;j++){
	if ( one[i]+one[j]>m)continue;
	two[p++]=one[i]+one[j];
	if (two[p-1]>maxv)maxv=two[p-1];
      }
    }
    sort(one,one+n);
    sort(two,two+p);
    for(int i=0;i<p;i++){
      if ( two[i]+one[0]>m)break;
      //      if ( two[i]+two[0]<=m)solve(two[i],m,two,p);
      //if ( two[i]+one[0]<=m)solve(two[i],m,one,n);
      solve(two[i],m,two,p);
      solve(two[i],m,one,n);
    }
    printf("%u\n",maxv);
  }
  return false;
}

C++: #include<stdio.h>
#include<iostream>
#include<algorithm>
using namespace std;
int main(){
while(1){
int i,j,n,m,o=1,s=0;
static int p[1001]={0},up[1001*1001]={0};
scanf("%d%d",&n,&m);
if(n==0&&m==0)return 0;
for(i=1;i<=n;i++){
scanf("%d",&p[i]);
for(j=i;j>0;j--){
up[o]=p[i]+p[j];
o++;
}
}
sort(up,up+o);
for(i=0;i<o;i++)s=max(s,up[i]+*(upper_bound(up,up+o,m-up[i])-1));
printf("%d\n",s);
}
return 0;
}

C++: #include<bits/stdc++.h>
using namespace std;
#define inf 1e9
#define ll long long
#define ull unsigned long long
#define M 1000000007
#define P pair<int,int>
#define PLL pair<ll,ll>
#define FOR(i,m,n) for(int i=(int)m;i<(int)n;i++)
#define RFOR(i,m,n) for(int i=(int)m;i>=(int)n;i--)
#define rep(i,n) FOR(i,0,n)
#define rrep(i,n) RFOR(i,n,0)
#define all(a) a.begin(),a.end()
#define IN(n,a) rep(i,n){ cin>>a[i]; }
const int vx[4] = {0,1,0,-1};
const int vy[4] = {1,0,-1,0};
#define PI 3.14159265


void f(int n,int m){
  int a[1000000];
  rep(i,n){
    cin>>a[i];
  }
  a[n]=0;

  vector<int> b;
  rep(i,n+1){
    FOR(j,i,n+1){
      b.push_back(a[i]+a[j]);
    }
  }
  sort(all(b));
  int ans = 0;

  for(int c : b){
    if(c>m) continue;
    int x =*(lower_bound(b.begin(),b.end(),m-c)-1);
    ans = max(ans,x+c);
  }

  cout<<ans<<endl;

}
int main(){
  int n,m;
  while(1){
    cin>>n>>m;
    if(n==0) break;
    f(n,m);
  }
}

C++: #include <bits/stdc++.h>
using namespace std;

#define for_(i,a,b) for(int i=(a);i<(b);++i)

int main() {
	int N, M;
	
	while (cin >> N >> M, N) {
		vector< int > P(N);
		for_(i,0,N) cin >> P[i];
		
		sort(P.begin(), P.end(), greater< int >());
		
		int cnt = 0, ans = 0;
		for_(i,0,N) {
			if (ans + P[i] <= M) ans += P[i], ++cnt, --i;
			if (cnt == 4) break;
		}
		cout << ans << endl;
	}
}

C++: #include<bits/stdc++.h>
#define LL long long
#define rep(i,n) for(int i=0;i<n;i++)
#define FOR(i,a,b) for(int i=a;i<=b;i++)
using namespace std;
static const LL INF = 1LL<<61LL;
typedef pair<int,int> PII;

int n,m;
int s[1010];
LL ans;
vector<LL> V;
int main(){
    while(1){
        cin>>n>>m;
        if(n==0&&m==0)break;
        V.clear();
        FOR(i,1,n)cin>>s[i];
        rep(i,n+1)rep(j,i+1){
            if(s[i]+s[j]<=m)V.push_back(s[i]+s[j]);
        }
        sort(V.begin(),V.end());
        int s=0; LL e=V.size()-1;
        while(s<=e){
            if(V[s]+V[e]>m){
                while(1){
                    if(V[s]+V[e]<=m)break;
                    e--;
                }
            }
            ans=max(ans,V[s]+V[e]);
            s++;
        }
        cout<<ans<<endl;
        ans=0;
    }
}

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

int main(){
	int n,m;
	int p[1001];
	int wa[1001 * 1001];
	while(1){
	cin >> n >> m;
	if(!n && !m) break;
	int ma = 0;
	for(int i = 0;i < n;i++) cin >> p[i];
	p[n] = 0;
	for(int i = 0;i < n + 1;i++){
		for(int j = 0;j < n + 1;j++) wa[i * (n + 1) + j] = p[i] + p[j];
	}
	sort(wa,wa + (n + 1) * (n + 1));
	for(int i = 0;i < n + 1;i++){
		for(int j = 0;j < n + 1;j++){
			int up = upper_bound(wa,wa + (n + 1) * (n + 1),m - (p[i] + p[j])) - wa,low = lower_bound(wa,wa + (n + 1) * (n + 1),m - (p[i] + p[j])) - wa;
			if(up - low == 0){
				if(low != 0) ma = max(ma,p[i] + p[j] + wa[low - 1]);
			}else if(up - low == 1){
				ma = m;
			}
		}
	}
	cout << ma << endl;
	}
	return 0;	
}

C++: #include<cstdio>
#include<cstring>
#include<algorithm>
#include<functional>
int t[1001*1001];
using namespace std;
int main(void)
{	
	int  n,p[1001],s,m,i,j,k,x,high,low,mid,max,suu,flg,mx;
	while(1) {
		scanf("%d %d",&n,&m);
		if(n==0 && m==0) break;
		p[0]=0;
		for(i=1;i<=n;i++) scanf("%d",&p[i]);
		x=0;
		for(i=0;i<=n;i++){
			for(j=0;j<=n;j++) {
				t[x]=p[i]+p[j];
				x++;
			}
		}
		sort(t,t+x);
		max=-1;
		mx=-1;
		for(i=0;i<x;i++) {
			flg=0;
			low=0;
			high=x;
			while(low<=high) {
				mid=(low+high)/2;
				if(t[mid]==m-t[i]) {
					flg=1;
					break;
				}
				if(t[mid]<m-t[i]) low=mid+1;
				else if(t[mid]>m-t[i]) high=mid-1;
			}
			if(flg==1) break; 
			else {
				if(t[high]+t[i]>m){}
				else {
					if(max<t[high]+t[i])
						max=t[high]+t[i];
				}
			}
		}
		if(flg==1) printf("%d\n",m);
		else printf("%d\n",max);
	}
	return 0;
}