/*
排序+LIS
O(n*n)做法可以的60分
刚开始打的n*n的最长上升子序列
*/
/*
排序时一点小技巧
把结构体按长从小到大排序
如果长相等则把宽大的排前面
这样就可以转化成求宽的最长上升子序列了
*/
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define maxn 50010
using namespace std;
struct node
{
int l;
int s;
}e[maxn*6];
int n,tot,len,c[maxn*6];
int cmp(node x,node y)
{
if(x.l<y.l)return 1;
if(x.l==y.l&&x.s>=y.s)return 1;
return 0;
}
int main()
{
int i,j,k;
scanf("%d",&n);
for(i=1;i<=n;i++)
{
int x,y,z;
scanf("%d%d%d",&x,&y,&z);
e[++tot].l=x;e[tot].s=y;
e[++tot].l=x;e[tot].s=z;
e[++tot].l=y;e[tot].s=z;
e[++tot].l=y;e[tot].s=x;
e[++tot].l=z;e[tot].s=x;
e[++tot].l=z;e[tot].s=y;
}
sort(e+1,e+tot+1,cmp);
for(i=1;i<=tot;i++)
{
if(e[i].s>c[len])
c[++len]=e[i].s;
else
{
//int mx=lower_bound(c+1,c+len+1,e[i].s)-c;
int l=1,r=len,mx;
while(l<=r)
{
int mid=(l+r)/2;
if(e[i].s<=c[mid])
{
mx=mid;
r=mid-1;
}
else
l=mid+1;
}
c[mx]=e[i].s;
}
}
printf("%d\n",len);
return 0;
}