#include "bits/stdc++.h"
using namespace std;
typedef long long ll;

template <typename TYPE>
void print_vec(const vector<TYPE>& v){
	for(int i=0; i<v.size(); i++){
		cout << v[i] << " ";
	}
	cout << endl;
}

template <typename TYPE>
void print_vec2(const vector<vector<TYPE>>& v){
  cout << endl; cout << "       ";
  for(int i=0; i<v[0].size(); i++) cout << i << "   "; 
  cout << endl;
	for(int i=0; i<v.size(); i++){
		cout << "i=" << i << ":   ";
		for(int j=0; j<v[i].size(); j++){
			if(v[i][j] == 0) cout << "\x1B[0m" << v[i][j] << "   ";
      else cout << "\x1B[31m" << v[i][j] << "   ";//https://stackoverrun.com/ja/q/12618775
		}
		cout << "\x1B[0m" << endl;
	}
}

////////////////////////////////////////////////////////////////

int chmin(int &a, int b){return a = min(a, b);}

int main(void) {
	int MAX = 0;
	vector<int> input;
	while(true){
		int x;
		cin >> x;
		if(x == 0) break;
		input.push_back(x);
		MAX = max(MAX, x);
	}

	const int TETRA_MAX = 1000;
	// dp1[i]: 正整数iを作るときに必要な四面体数の最小個数
	vector<int> dp1(MAX+1, MAX+1);
	dp1[0] = 0;
	for(int i=0; i<TETRA_MAX; i++){
		int tetra = (i+1)*(i+2)*(i+3)/6;
		for(int j=0; j<=MAX; j++){
			//chmin(dp1[j], dp1[j]);
			if(j+tetra <= MAX) chmin(dp1[j+tetra], dp1[j]+1);//これだと 同じ四面体数を複数回使うことを考慮できてないと思われる
			//if(j+tetra <= MAX) chmin(dp1[j+tetra], dp1[j]+1);
	
			//if(j-tetra >= 0) chmin(dp1[j], dp1[j-tetra] + 1);//もらうdp
		}	
	}	

	// vector<ll> odd_tetras;
	// for(int i=0; i<TETRA_MAX; i++){
	// 	ll tetra = (i+1)*(i+2)*(i+3)/6;
	// 	if(tetra % 2 == 0) continue;
	// 	odd_tetras.push_back(tetra);
	// }
	// dp2[i]: 正整数iを作るときに必要な奇数の四面体数の最小個数
	vector<int> dp2(MAX+1, MAX+1);
	dp2[0] = 0;
	for(int i=0; i<TETRA_MAX; i++){
		int tetra = (i+1)*(i+2)*(i+3)/6;
		if(tetra % 2 == 0) continue;
		for(int j=0; j<=MAX; j++){
			//chmin(dp2[j], dp2[j]);
			if(j+tetra <= MAX) chmin(dp2[j+tetra], dp2[j]+1);//これだと 同じ四面体数を複数回使うことを考慮できてないと思われる
			//if(j+tetra <= MAX) chmin(dp2[j+tetra], dp2[j]+1);

			//if(j-tetra >= 0) chmin(dp2[j], dp2[j-tetra] + 1);//もらうdp
		}	
	}	

	for(int i=0; i<(int)input.size(); i++){
		cout << dp1[input[i]] << " " << dp2[input[i]] << endl;
	}


	//以下2次元のdp　だけど メモリエラーになったので1次元でやりましょう
	// const int TETRA_MAX = 100;
	// // dp1[i][j]: (i-1)番目までの四面体数を使って，正整数jを作るときに必要な四面体数の最小個数
	// vector<vector<ll>> dp1(TETRA_MAX+1, vector<ll>(MAX+1, MAX+1));
	// dp1[0][0] = 0;
	// for(ll i=0; i<TETRA_MAX; i++){
	// 	ll tetra = (i+1)*(i+2)*(i+3)/6;
	// 	for(int j=0; j<=MAX; j++){
	// 		chmin(dp1[i+1][j], dp1[i][j]);
	// 		if(j+tetra<=MAX) chmin(dp1[i+1][j+tetra], dp1[i][j]+1);
	// 		if(j+tetra<=MAX) chmin(dp1[i+1][j+tetra], dp1[i+1][j]+1);
	// 	}
	// }

	// vector<ll> odd_tetras;
	// for(int i=0; i<TETRA_MAX; i++){
	// 	ll tetra = (i+1)*(i+2)*(i+3)/6;
	// 	if(tetra % 2 == 0) continue;
	// 	odd_tetras.push_back(tetra);
	// }
	
	// //dp2[i][j]: (i-1)番目までの四面体数の中の奇数のモノのみを使って，
	// //正整数jを作るときに必要な四面体数の最小個数
	// vector<vector<ll>> dp2(odd_tetras.size()+1, vector<ll>(MAX+1, MAX+1));
	// dp2[0][0] = 0;
	// for(int i=0; i<dp2.size()-1; i++){
	// 	ll tetra = odd_tetras[i];
	// 	for(int j=0; j<=MAX; j++){
	// 		chmin(dp2[i+1][j], dp2[i][j]);
	// 		if(j+tetra<=MAX) chmin(dp2[i+1][j+tetra], dp2[i][j]+1);
	// 		if(j+tetra<=MAX) chmin(dp2[i+1][j+tetra], dp2[i+1][j]+1);
	// 	}
	// }
	
	

	// for(int i=0; i<input.size(); i++){
	// 	cout << dp1[dp1.size()-1][input[i]] << " " << dp2[dp2.size()-1][input[i]] <<  endl;
	// }
	

}	



Measured memory_bytes: 10440