#include<bits/stdc++.h>
#define range(i,a,b) for(int i = (a); i < (b); i++)
#define rep(i,b) for(int i = 0; i < (b); i++)
#define all(a) (a).begin(), (a).end()
#define show(x)  cerr << #x << " = " << (x) << endl;
using namespace std;

class boolean;
template<typename T> class Value;

class boolean{
	bool b;
	public:
	boolean() { }
	boolean(bool b) : b(b) { }

	void operator = (const bool b){
		this->b = b;
	}

	boolean And(boolean a){ return b and a.get(); };
	boolean Or(boolean a){ return b or a.get(); };
	boolean Xor(boolean a){ return b xor a.get(); };

	template<typename X> Value<X> ter(X x, X y){ return b ? x : y; };

	bool get(){ return b; }
	void out(string f = "Yes", string s = "No"){
		cout << (b ? f : s) << endl;
	}
};

template<typename T>
class Value{
	T value;

	public:

	Value() { }
	Value(T value) : value(value) { }

	Value<T> add(Value<T> a){ return Value<T>(value + a.get()); }
	Value<T> sub(Value<T> a){ return Value<T>(value - a.get()); }
	Value<T> pro(Value<T> a){ return Value<T>(value * a.get()); }
	Value<T> div(Value<T> a){ return Value<T>(value / a.get()); }
	Value<T> mod(Value<T> a){ return Value<T>(value % a.get()); }

	Value<T> sqrt(){
		for(int i = 1; i * i <= value; i++){
			if(i * i == value) return i;
		}
		return -1;
	}
	Value<T> abs(){ return std::abs(value); }

	boolean eq(Value<T> a){ return value == a.get(); }
	boolean neq(Value<T> a){ return value != a.get(); }
	boolean seq(Value<T> a){
		assert(typeid(a.get()) == typeid(string));
		std::set<char> x, y;
		for(auto i : value) x.emplace(i);
		for(auto i : a.get()) y.emplace(i);
		return x == y;
	}
	boolean gt(Value<T> a){ return value > a.get(); }
	boolean gtq(Value<T> a){ return value >= a.get(); }
	boolean lt(Value<T> a){ return value < a.get(); }
	boolean ltq(Value<T> a){ return value <= a.get(); }

	boolean even(){ return value % 2 == 0; }
	boolean odd(){ return value % 2 == 1; }


	Value<T> max(Value<T> a){ return value < a.get() ? a : *this; }
	Value<T> min(Value<T> a){ return value < a.get() ? *this : a; }

	T get(){ return value; }
	void set(T v){ value = v; }

	auto begin(){ return value.begin(); }
	auto end(){ return value.end(); }

	void out(){ cout << value << endl; };
};


/* output */
template<typename T>
ostream& operator << (ostream& os, Value<T> t){
	os << t.get();
	return os;
}
void yn(bool b){
	cout << (b ? "Yes" : "No") << endl;
}
template<typename T> void out(T a){
	cout << a << endl;
}
template<typename T> void out(vector<T> a, bool space = true){
	rep(i,a.size()){
		cout << a[i] << (i + 1 == a.size() ? "\n" : (space ? " " : ""));
	}
}
template<typename T> void out(vector<vector<Value<T>>>& v){
	rep(i,v.size()){
		out(v[i]);
	}
}

/* 多重vector */
template <typename X, typename T>
auto vectors(X x, T a) {
	return vector<T>(x, a);
}

template <typename X, typename Y, typename Z, typename... Zs>
auto vectors(X x, Y y, Z z, Zs... zs) {
	auto cont = vectors(y, z, zs...);
	return vector<decltype(cont)>(x, cont);
}

/* input */
template<typename T>
istream& operator >> (istream& is, Value<T>& t){
	T res;
	is >> res;
	t.set(res);
	return is;
}

template<typename T> T in(){
	T res;
	cin >> res;
	return res;
}
template<typename T> vector<T> in(int n){
	vector<T> res(n);
	rep(i,n) res[i] = in<T>();
	return res;
}
template<typename T> vector<vector<T>> in(int h, int w){
	vector<vector<T>> res(h);
	rep(i,h) res[i] = in<T>(w);
	return res;
}

struct Type{
	using T = int;
	static constexpr int Number(){ return 4; }
};

typedef typename Type::T S;
typedef Value<S> V;
typedef vector<V> Vec;

void solve(){
	Vec a = in<V>(Type::Number());

	int ans = 0;
	rep(i,a[0].get() + 1){
		rep(j,a[1].get() + 1){
			rep(k,a[2].get() + 1){
				if(i * 500 + j * 100 + k * 50 == a[3].get()) ans++;
			}
		}
	}
	out(ans);
}


int main(){
	solve();
}


Measured memory_bytes: 256