#include using namespace std; #define REP(i,a,n) for(int i=(a); i<(int)(n); i++) #define rep(i,n) REP(i,0,n) #define FOR(it,c) for(__typeof((c).begin()) it=(c).begin(); it!=(c).end(); ++it) #define ALLOF(c) (c).begin(), (c).end() typedef long long ll; typedef unsigned long long ull; struct ST{ int X, Y, Z; }; class SCC { public: static const int MAX_V = 1005; vector G[MAX_V]; vector rG[MAX_V]; vector vs; bool used[MAX_V]; int V; int cmp[MAX_V]; void add_edge(int from, int to){ G[from].push_back(to); rG[to].push_back(from); } private: void dfs(int v){ used[v] = true; for(int i=0; i=0; i--) if(!used[vs[i]]) rdfs(vs[i], k++); return k; } }; bool can_in(const ST& a, const ST& b){ if(a.X < b.X && a.Y < b.Y && a.Z < b.Z) return true; if(a.X < b.X && a.Y < b.Z && a.Z < b.Y) return true; if(a.X < b.Y && a.Y < b.X && a.Z < b.Z) return true; if(a.X < b.Y && a.Y < b.Z && a.Z < b.X) return true; if(a.X < b.Z && a.Y < b.X && a.Z < b.Y) return true; if(a.X < b.Z && a.Y < b.Y && a.Z < b.X) return true; return false; } int main(){ int N; cin >> N; vector v; rep(i,N){ int X, Y, Z; cin >> X >> Y >> Z; v.push_back((ST){X,Y,Z}); } SCC scc; scc.V = N; rep(i,N){ rep(j,N){ if(i == j) continue; if(can_in(v[i], v[j])){ scc.add_edge(i,j); } } } scc.calc(); vector> order; rep(i,N){ order.push_back(make_pair(scc.cmp[i],i)); } sort(ALLOF(order)); vector dp(N, 1); rep(i,N){ int node = order[i].second; rep(j,scc.G[node].size()){ dp[scc.G[node][j]] = max(dp[scc.G[node][j]], dp[node]+1); } } int ret = 0; rep(i,dp.size()){ ret = max(ret, dp[i]); } cout << ret << endl; return 0; }