#include <cstdio>
#include <iostream>
#include <vector>
#include <list>
#include <cmath>
#include <fstream>
#include <algorithm>
#include <string>
#include <queue>
#include <set>
#include <map>
#include <complex>
#include <iterator>
#include <cstdlib>
#include <cstring>
#include <sstream>

using namespace std;

const double EPS=(1e-10);
typedef long long ll;
typedef pair<int,int> pii;
bool EQ(double a,double b){
  return abs((a)-(b))<EPS;
}
void fast_stream(){
	std::ios_base::sync_with_stdio(0);
}

const int MAX_V = 10000;

struct edge{
  int to,cap,cost,rev;
};

int V;
vector<edge> G[MAX_V];
vector<edge> G2[MAX_V];
int dist[MAX_V];
int h[MAX_V]; // |eV

// ¼OÌ¸_ÆÓ
int prevv[MAX_V];
int preve[MAX_V];

const int INF = 100000000;

// firstÍÅZ£AsecondÍ¸_ÌÔ
typedef pair<int,int> P;

// from©çtoÖÞ©¤eÊcap,RXgcostÌÓðOtÉÇÁ·éB
void add_edge(int from,int to,int cap,int cost){	
    edge e;
    e.to = to,e.cap = cap,e.cost = cost,e.rev = G[to].size();
    G[from].push_back(e);
    e.to = from,e.cap = 0,e.cost = -cost,e.rev = G[from].size()-1;
    G[to].push_back(e);
}

// s©çtÖÌ¬ÊfÌÅ¬ïp¬ðßé
// Èª¹È¢êÍ-1ðÔ·
pii min_cost_flow(int s,int t,int f){
    for(int i=0;i<V;i++)G2[i]=G[i];
    int res = 0;
    fill(h,h+V,0);
    // ¬ÊªÀEÉB·éÜÅ¬·
    int a=0;
    int b=f;
    while(f > 0){
        // _CNXg@ÅAÅZ£ðõ
        priority_queue<P,vector<P>,greater<P> > que;
        fill(dist,dist+V,INF);
        dist[s] = 0;
        que.push(P(0,s));
        while(!que.empty()){
            P p = que.top();
            que.pop();
            int v = p.second;
            if(dist[v] < p.first)
                continue;
            for(int i = 0; i < G2[v].size(); i++){
                edge &e = G2[v][i];
                if(e.cap > 0 && dist[e.to] > dist[v] + e.cost + h[v] - h[e.to]){
                    dist[e.to] = dist[v] + e.cost + h[v] - h[e.to];
                    prevv[e.to] = v;
                    preve[e.to] = i;
                    que.push(P(dist[e.to],e.to));
                }
            }
        }

        if(dist[t] == INF)
            return pii(a,res);
        a++;
        for(int i = 0; i < V; i++)
            h[i] += dist[i];

        int d = f;
        for(int v = t; v != s; v = prevv[v]){
            d = min(d,G2[prevv[v]][preve[v]].cap);
        }
        f -= d;
        res += d*h[t];
        for(int v = t; v != s; v = prevv[v]){
            edge &e = G2[prevv[v]][preve[v]];
            e.cap -= d;
            G2[v][e.rev].cap += d;
        }
    }
    return pii(b,res);
}

int N;
int M[1001];
// m[hÌîñ©çm[hÔðæèo·
map<int,int> idxs[2][110];
int X[101][21];
int Y[101][21];
int C[101][21];
int g;

void solve(){
    while(cin>>N&&N){
        for(int i=0;i<2;i++)for(int j=0;j<110;j++)idxs[i][j].clear();
        for(int i=0;i<MAX_V;i++)G[i].clear();
        V=0;
        for(int i=1;i<N;i++){
            cin>>M[i];
            for(int j=0;j<M[i];j++)cin>>X[i][j]>>Y[i][j]>>C[i][j];
        }
        cin>>g;
        // start
        idxs[1][1][0]=V++;
        for(int q=1;q<N;q++){
            for(map<int,int>::iterator it=idxs[1][q].begin();it!=idxs[1][q].end();it++){
                int time=it->first;
                for(int j=0;j<M[q];j++){
                    // »ÝÌªo­æè¬³¢
                    if(X[q][j]>=time){
                        if(idxs[0][q+1].count(Y[q][j])==0)idxs[0][q+1][Y[q][j]]=V++;
                        add_edge(it->second,idxs[0][q+1][Y[q][j]],1,C[q][j]);
                    }
                }
            }
            // »ê¼êÌm[h©çAoRm[hÖGbWðÔ
            for(map<int,int>::iterator it=idxs[0][q+1].begin();it!=idxs[0][q+1].end();it++){
                int time=it->first;
                if(idxs[1][q+1].count(it->first)==0)idxs[1][q+1][it->first]=V++;
                add_edge(it->second,idxs[1][q+1][it->first],1,0);
            }
        }
        idxs[0][N+1][0]=V++;
        // NÌm[h©çAS[ÖGbWðÔ
        for(map<int,int>::iterator it=idxs[1][N].begin();it!=idxs[1][N].end();it++){
            add_edge(it->second,idxs[0][N+1][0],1,0);
        }
        int sp=0;
        int gp=V-1;
        pii res=min_cost_flow(sp,gp,g);
        if(res.first!=0)
            cout<<res.first<<" "<<res.second<<endl;
        else cout<<0<<" "<<0<<endl;
    }
}
int main(){

    solve();

    return 0;
}

Measured memory_bytes: 0