#include<iostream>
#include<string>
#include<cstdio>
#include<vector>
#include<cmath>
#include<algorithm>
#include<functional>
#include<iomanip>
#include<queue>
#include<ciso646>
#include<random>
#include<map>
#include<set>
#include<complex>
#include<bitset>
#include<stack>
#include<unordered_map>
#include<utility>
#include<cassert>
using namespace std;

typedef long long  ll;

typedef unsigned long long ul;
typedef unsigned int ui;
const ll mod = 1000000007;
typedef double ld;
typedef complex<ld> Point;
const ll INF = mod * mod;
typedef pair<int, int> P;
#define stop char nyaa;cin>>nyaa;
#define rep(i,n) for(int i=0;i<n;i++)
#define per(i,n) for(int i=n-1;i>=0;i--)
#define Rep(i,sta,n) for(int i=sta;i<n;i++)
#define rep1(i,n) for(int i=1;i<=n;i++)
#define per1(i,n) for(int i=n;i>=1;i--)
#define Rep1(i,sta,n) for(int i=sta;i<=n;i++)
const ld eps = 1e-8;
const ld pi = acos(-1.0);
typedef pair<ld, ld> LDP;
typedef pair<ll, ll> LP;
typedef vector<int> vec;
typedef vector<string> svec;

bool isalf(char t) {
	if ('a' <= t && t <= 'z')return true;
	return false;
}
bool isAlf(char t) {
	if ('A' <= t && t <= 'Z')return true;
	return false;
}

ll dp[52][52][52],cop[52][52][52];
//ATGC

void solve() {
	int c[4] = {};
	rep(i, 4)cin >> c[i];
	int m; cin >> m;
	string s; getline(cin, s);
	map<string, int> mp;
	vector<svec> v(m);
	rep(i, m) {
		getline(cin, s);
		int len = s.size();
		string str;
		rep(j, len) {
			if (s[j] == ':') {
				str = s.substr(0, j);
				break;
			}
		}
		mp[str] = i;
		Rep(j, str.size()+1, len) {
			if (s[j] == '[') {
				int ri = j;
				while (s[ri] != ']')ri++;
				string u = s.substr(j + 1, ri - j - 1);
				v[i].push_back(u);
				j = ri;
			}
			else if (isalf(s[j])) {
				int ri = j;
				while (ri + 1 < len&&isalf(s[ri + 1]))ri++;
				string u = s.substr(j, ri - j + 1);
				v[i].push_back(u);
				j = ri;
			}
		}
	}
	vector<int> num(m);
	per(i, m) {
		rep(j, v[i].size()) {
			string &s = v[i][j];
			if (isalf(s[0])) {
				int id = mp[s];
				num[i] += num[id];
			}
			else {
				num[i]++;
			}
		}
		if (num[i] > 200) {
			cout << 0 << endl; return;
		}
	}
	int z = 0;
	rep(i, 4)z += c[i];
	if (z != num[0]) {
		cout << 0 << endl; return;
	}
	vector<vec> memo[50];
	per(i, m) {
		rep(j, v[i].size()) {
			string &s = v[i][j];
			if (isAlf(s[0])) {
				vec nex(4, 0);
				rep(k, s.size()) {
					if (s[k] == 'A')nex[0] = 1;
					else if (s[k] == 'T')nex[1] = 1;
					else if (s[k] == 'G')nex[2] = 1;
					else nex[3] = 1;
				}
				memo[i].push_back(nex);
			}
			else {
				int id = mp[s];
				rep(k, memo[id].size()) {
					memo[i].push_back(memo[id][k]);
				}
			}
		}
	}
	vector<vec> &u = memo[0];
	dp[0][0][0] = 1;
	rep(i, z) {
		rep(j, 51) {
			rep(k, 51) {
				rep(l, 51) {
					cop[j][k][l] = 0;
				}
			}
		}
		vec &t = u[i];
		rep(j, 51) {
			rep(k, 51) {
				rep(l, 51) {
					if (t[0]) {
						cop[j + 1][k][l] += dp[j][k][l];
					}
					if (t[1]) {
						cop[j][k + 1][l] += dp[j][k][l];
					}
					if (t[2]) {
						cop[j][k][l + 1] += dp[j][k][l];
					}
					if (t[3]) {
						cop[j][k][l] += dp[j][k][l];
					}
				}
			}
		}
		rep(j, 51) {
			rep(k, 51) {
				rep(l, 51) {
					dp[j][k][l] = cop[j][k][l] % mod;
				}
			}
		}
	}
	cout << dp[c[0]][c[1]][c[2]] << endl;
}

int main() {
	ios::sync_with_stdio(false);
	cin.tie(0);
	//cout << fixed << setprecision(5);
	//while (cin >> w>>h>>n,n)solve();
	solve();
	//stop
	return 0;
}



Measured memory_bytes: 5484