// インクルード(GCC only)
#include <bits/stdc++.h>

// 長い型名
using namespace std;
typedef long long LL;
typedef pair<LL, LL> P;

// 省略記法
#define INF 1e9
#define rep(i,n) for(int i=0, i##_len=(n); i<i##_len; ++i)
#define rrep(i,n) for(int i##_len=(n), i=(i##_len-1); i>=0; ++i)
#define FOR(i,m,n) for(int i=(m), i##_len=(n); i<i##_len; ++i)
#define all(x) (x).begin(),(x).end()
#define sizei(x) ((int)(x).size())
#define fill(x,y) memset(x,y,sizeof(x))
#define printvector(x) rep(i,sizei(x)){cout << x[i] << endl;}
template<class T>bool chmax(T &a, const T &b) { if (a<b) { a=b; return 1; } return 0; }
template<class T>bool chmin(T &a, const T &b) { if (b<a) { a=b; return 1; } return 0; }

// デバッグ用
#ifdef LOCAL
    #define eprint(...) fprintf(stderr, __VA_ARGS__)
    #define eprintvector(x) printvector(x)
#else
    #define eprint(...) 42
    #define eprintvector(x) 42
#endif

#define SIZE 1000
typedef tuple<LL,int,int,int> TTT;

int main(void)
{
  int X, Y, Z, K;
  cin >> X >> Y >> Z >> K;

  vector<LL> A(X), B(Y), C(Z);
  rep(i, X) cin >> A[i];
  rep(i, Y) cin >> B[i];
  rep(i, Z) cin >> C[i];

  // method 1
  // vector<LL> E;
  // rep(i, X) {
  //   rep(j, Y) {
  //     E.push_back(A[i] + B[j]);
  //   }
  // }
  // sort(all(E), greater<LL>());
  // sort(all(C), greater<LL>());
  //
  // vector<LL> ANS;
  // rep(i, min(X*Y, K)) {
  //   rep(j, min(Z, K)) {
  //     ANS.push_back(E[i] + C[j]);
  //   }
  // }
  // sort(all(ANS), greater<LL>());
  // printvector(ANS);
  //
  // rep(i, min(X*Y*Z, K)) {
  //   cout << ANS[i] << endl;
  // }

  // method 2
  // sort(all(A), greater<LL>());
  // sort(all(B), greater<LL>());
  // sort(all(C), greater<LL>());
  //
  // vector<LL> ANS;
  //
  // rep(i, X) {
  //   rep(j, Y) {
  //     rep(k, Z) {
  //       if ((i + 1)*(j + 1)*(k + 1) <= K) ANS.push_back(A[i] + B[j] + C[k]);
  //       else break;
  //     }
  //   }
  // }
  //
  // sort(all(ANS), greater<LL>());
  //
  // rep(i, K) {
  //   cout << ANS[i] << endl;
  // }

  // method 3 (優先度付きキュー何もわからん!!!)
  auto c = [](TTT a, TTT b){ return (get<0>(a) < get<0>(b)); };
  priority_queue<TTT, vector<TTT>, decltype(c)> que(c);

  sort(all(A), greater<LL>());
  sort(all(B), greater<LL>());
  sort(all(C), greater<LL>());

  que.push(make_tuple(A[0] + B[0] + C[0], 0, 0, 0));

  map<LL, bool> used;
  int count = 0;
  used[0] = true;
  while (!que.empty() && count < K) {
    TTT t = que.top(); que.pop();
    cout << get<0>(t) << endl;
    int i = get<1>(t);
    int j = get<2>(t);
    int k = get<3>(t);
    if (i < X-1 && !used[(i+1)*SIZE*SIZE + j*SIZE + k]) {
      eprint("%d, %d, %d\n", i+1, j, k);
      used[(i+1)*SIZE*SIZE + j*SIZE + k] = true;
      que.push(make_tuple(A[i+1] + B[j] + C[k], i+1, j, k));
    }
    if (j < Y-1 && !used[i*SIZE*SIZE + (j+1)*SIZE + k]) {
      eprint("%d, %d, %d\n", i, j+1, k);
      used[i*SIZE*SIZE + (j+1)*SIZE + k] = true;
      que.push(make_tuple(A[i] + B[j+1] + C[k], i, j+1, k));
    }
    if (k < Z-1 && !used[i*SIZE*SIZE + j*SIZE + (k+1)]) {
      eprint("%d, %d, %d\n", i, j, k+1);
      used[i*SIZE*SIZE + j*SIZE + (k+1)] = true;
      que.push(make_tuple(A[i] + B[j] + C[k+1], i, j, k+1));
    }
    count ++;
  }

  return 0;
}


Measured memory_bytes: 896