There are N people numbered 1 to N. Each of them is either an honest person whose testimonies are always correct or an unkind person whose testimonies may be correct or not.
Person i gives A_i testimonies. The j-th testimony by Person i is represented by two integers x_{ij} and y_{ij}. If y_{ij} = 1, the testimony says Person x_{ij} is honest; if y_{ij} = 0, it says Person x_{ij} is unkind.
How many honest persons can be among those N people at most?

-----Constraints-----
 - All values in input are integers.
 - 1 \leq N \leq 15
 - 0 \leq A_i \leq N - 1
 - 1 \leq x_{ij} \leq N
 - x_{ij} \neq i
 - x_{ij_1} \neq x_{ij_2} (j_1 \neq j_2)
 - y_{ij} = 0, 1

-----Input-----
Input is given from Standard Input in the following format:
N
A_1
x_{11} y_{11}
x_{12} y_{12}
:
x_{1A_1} y_{1A_1}
A_2
x_{21} y_{21}
x_{22} y_{22}
:
x_{2A_2} y_{2A_2}
:
A_N
x_{N1} y_{N1}
x_{N2} y_{N2}
:
x_{NA_N} y_{NA_N}

-----Output-----
Print the maximum possible number of honest persons among the N people.

-----Sample Input-----
3
1
2 1
1
1 1
1
2 0

-----Sample Output-----
2

If Person 1 and Person 2 are honest and Person 3 is unkind, we have two honest persons without inconsistencies, which is the maximum possible number of honest persons.

Difficulty: introductory

Starter code:

Solutions:
#ABC147　C　やってる途中
n=int(input())
l=[]
for i in range(n):
  a=int(input())
  l_=[]
  for j in range(a):
    xy=list(map(int,input().split()))
    l_.append(xy)
  l.append(l_)
ans=0
for i in range(2**n):
  table=[0]*n
  flag=False
  for j in range(n):
    if (i>>j)&1:
      table[j]=1
  for j in range(n):
    for k in l[j]:
   
      if k[1]!=table[k[0]-1] and table[j]==1:
        flag=True
        break

        if flag:
          break

  if flag==True:
    continue


  ans = max(ans, table.count(1))


print(ans)

N=int(input())
A=[[]for _ in range(N)]
for i in range(N):
    for _ in range(int(input())):
        A[i].append(list(map(int,input().split())))

ans=[]
for i in range(2**N):
    Bit = [1]*N
    for j in range(N):
        if (i >> j) & 1:
            Bit[j] = 0
    i=0
    no=0
    while i<N:
        if Bit[i]==1:
            for x,y in A[i]:
                if Bit[x-1]!=y:
                    no=1
        i+=1
    if no:
        ans.append(0)
    else:
        ans.append(Bit.count(1))

print(max(ans))

N = int(input())
A = []
for _ in range(N):
    a = int(input())
    b = []
    for _ in range(a):
        b.append(list(map(int, input().split())))
    A.append(b)
# 証言リスト A[i人目][j個目の証言] -> [誰が, bit(1は正、0は誤)]

# bitが1であれば正しい証言、0であれば間違った証言とする
# 正しい証言だけ確認して、[i, 1]と証言した i も1かどうか、[j,0]と証言したjが0かどうか



def F(i):
    cnt = 0
    B = [-1]*N                #B = [-1,-1,-1]
    r = 0
    for j in range(N):    # i=1,  j=0,1,2
        if (i>>j)&1:         # 001 ->  1,0,0  j=0
            r += 1               # r = 1    
            if B[j] == 0:     #B[0] == -1  
                return 0
            B[j]=1              # B = [1,-1,-1]   
            for p,q in A[j]: # A[0] = [[2, 1], [3, 0]]   
                if q == 0:
                    if B[p-1]==1:  # B[2] == -1
                        return 0
                    B[p-1] = 0  # B = [1,1,0]
                else:
                    if B[p-1]==0:  # B[1] == -1
                        return 0
                    B[p-1] = 1      # B = [1,1,-1]
            else:
                cnt += 1          # cnt = 1
        else:         # j=1
            if B[j]==1:       #B[1] ==1
                return 0
            B[j]=0
            
    if cnt == r:
        return cnt

ans = 0
for i in range(1<<N):
    ans = max(ans,F(i))
print(ans)

n=int(input())
s=[]
for i in range(n):
    a=int(input())
    s_i=[]
    for j in range(a):
        x,y=map(int,input().split())
        s_i.append([x-1,y])
    s.append(s_i)

ans=0
for i in range(2**n):
    honest=[0]*n
    skip=False #矛盾があるときTrue
    for j in range(n):
        if ((i>>j)&1): honest[j]=1
    for j in range(n):
        if honest[j]==1:
            for k in range(len(s[j])):
                if honest[s[j][k][0]]!=s[j][k][1]:
                    skip=True
                    break
    if skip: continue
    ans=max(ans,sum(honest))
print(ans)


N = int(input())
testimo_ls = [ [] for i in range(N) ]
rst = 0
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split(' '))
        testimo_ls[i].append([x - 1, y])
for i in range(1 << N):
    honest_ls = []
    for j in range(N):
        if i >> j & 1:
            honest_ls.append(j)
    is_ok = True
    for s in honest_ls:
        for t in testimo_ls[s]:
            if t[1] == 0 and t[0] in honest_ls:
                is_ok = False
                break
            if t[1] == 1 and not t[0] in honest_ls:
                is_ok = False
                break
    if is_ok:
        rst = max(rst, len(honest_ls))
print(rst)

n = int(input())
a = []
x = []
y = []
for i in range(n):
    ai = int(input())
    a.append(ai)
    xi = []
    yi = []
    for j in range(ai):
        xij, yij = list(map(int, input().split(' ')))
        xi.append(xij)
        yi.append(yij)
    x.append(xi)
    y.append(yi)
ans = 0
for case in range(2**n):
    truth_t = 0  #正直者の真の数
    truth = 0    #正直者の確認した数
    for i in range(n):  #人ごとに矛盾が生じないか確認
        if (case>>i)&1:  #正直者であれば証言に矛盾がないか確認
            truth_t+=1
            proof=0
            for j in range(a[i]):
                if ((case>>(x[i][j]-1))&1)==y[i][j]:
                    proof+=1
            if proof==a[i]:
                truth += 1
    if truth==truth_t:
        if ans<truth:
            ans = truth
print(ans)


n = int(input())
a = []
x = []
y = []
for i in range(n):
    z = int(input())
    a.append(z)
    for j in range(z):
        s,r = map(int,input().split())
        x.append(s)
        y.append(r)
ans = 0
for i in range(2**n):
    t = [0] * n
    j = 0
    k = 0
    z = i
    while z > 0:
        if z % 2 != 0:
            t[j] = 1
            k += 1
        j += 1
        z = z // 2
    flg = True
    j = 0
    z = 0
    p = 0
    while j < n:
        if t[j] == 1:
            for q in range(a[z]):
                if t[x[p+q]-1] != y[p+q]:
                    flg = False
        p += a[z]
        j += 1
        z += 1
    if flg:
        ans = max(ans,k)
print(ans)

N = int(input())

arr = [[] for _ in range(N)]
for i in range(N):
  A = int(input())
  for a in range(A):
    x,y = map(int,input().split())
    arr[i].append((x-1,y))

ans = 0
for bit in range(1,1<<N):
  honest = set()
  unkind = set()
  h = set()
  for i in range(N):
    if bit & (1<<i):
      h.add(i)
      for x,y in arr[i]:
        if y:
          honest.add(x)
        else:
          unkind.add(x)

  # print(h,honest,unkind)
  if 0 == len(honest - h) and h.isdisjoint(unkind) and honest.isdisjoint(unkind):
    # print("   ",h,honest,unkind)
    ans = max(len(h), ans)
    
print(ans)

n = int(input())
xy = [[] for _ in range(n)]
for i in range(n):
    a = int(input())
    for j in range(a):
        x_,y_ = map(int,input().split())
        xy[i].append((x_-1,y_))
ans = 0
for i in range(1,2**n):
    flag = 0
    for j in range(n):
        if i>>j&1:
            for x,y in xy[j]:
                if i>>x&1 != y:
                    flag = 1 
                    break
    if flag==0:
        ans = max(ans, bin(i)[2:].count("1"))
print(ans)

#
# abc147 c
#
import sys
from io import StringIO
import unittest


class TestClass(unittest.TestCase):
    def assertIO(self, input, output):
        stdout, stdin = sys.stdout, sys.stdin
        sys.stdout, sys.stdin = StringIO(), StringIO(input)
        resolve()
        sys.stdout.seek(0)
        out = sys.stdout.read()[:-1]
        sys.stdout, sys.stdin = stdout, stdin
        self.assertEqual(out, output)

    def test_入力例_1(self):
        input = """3
1
2 1
1
1 1
1
2 0"""
        output = """2"""
        self.assertIO(input, output)

    def test_入力例_2(self):
        input = """3
2
2 1
3 0
2
3 1
1 0
2
1 1
2 0"""
        output = """0"""
        self.assertIO(input, output)

    def test_入力例_3(self):
        input = """2
1
2 0
1
1 0"""
        output = """1"""
        self.assertIO(input, output)


def resolve():
    N = int(input())
    C = []
    for i in range(N):
        a = int(input())
        C.append([list(map(int, input().split())) for j in range(a)])

    ans = 0
    for bit in range(1 << N):
        f = True
        for i in range(N):
            if bit & (1 << i):
                for c in C[i]:
                    if bit & (1 << c[0]-1) != (1 << c[0]-1)*c[1]:
                        f = False
                        break
        if f == True:
            ans = max(ans, bin(bit).count("1"))
    print(ans)


def __starting_point():
    # unittest.main()
    resolve()

__starting_point()

N = int(input())
shougen = [[] for _ in range(N)]
for k in range(N):
    A = int(input())
    for j in range(A):
        x, y = list(map(int, input().split()))
        x -= 1
        shougen[k].append((x, y))
ans = 0
bit = 2**N-1
while bit:
    person = [-1 for _ in range(N)]
    b = bit
    count = 0
    while count < N:
        person[count] = b & 1
        b >>= 1
        count += 1
    flag = True
    for k in range(N):
        if person[k] == 1:
            for x, y in shougen[k]:
                if person[x] != y:
                    flag = False
                    break
            else:
                continue
            break
    if flag:
        ans = max(ans, sum(person))
    bit -= 1
print(ans)



#!/usr/bin/env python3
def main():
    import numpy as np

    N = int(input())
    testimony = np.zeros((N, N), dtype=np.int64)
    for i in range(N):
        A = int(input())
        INF = 10 ** 10
        for _ in range(A):
            x, y = list(map(int, input().split()))
            testimony[i, x - 1] += 1 if y else -INF

    # 正直者のパターンをbit全探索
    ans = 0
    for bit in range(1 << N):
        honest = set()
        pick = np.zeros(N, dtype=np.int64)
        for i in range(N):
            if bit & (1 << i):
                honest.add(i)
                pick += testimony[i, :]
        flag = True
        for j in range(N):
            value = pick[j]
            # 下記3つの内1つでも満たしたら，仮定が間違っていると分かる.
            if (0
                    or (j in honest and value < 0)         # 正直者なのに嘘つきと言われる
                    or (j not in honest and value > 0)     # 嘘つきなのに正直者と言われる
                    or (value < 0 and value % INF != 0)):  # 正直とも嘘つきとも言われる
                flag = False
                break
        if flag:
            ans = max(ans, len(honest))
    print(ans)


def __starting_point():
    main()

__starting_point()

N = int(input())
A = [0 for n in range(N)]
XY = [0 for n in range(N)]
count_max = 0

for i in range(N):
  A[i] = int(input())
  xy = []
  for j in range(A[i]):
    x_y = list(map(int,input().split()))
    xy.append(x_y)
  XY[i] = xy

for i in range(2 ** N):
  op = [0]*N
  for j in range(N):  # ポイント１
    if ((i >> j) & 1):
      op[N-1-j] = 1
      
  flag = True
  
  for k in range(len(op)):
    if op[k] == 1:
      for l in range(A[k]):
        if XY[k][l][1] != op[XY[k][l][0]-1]:
          flag = False
        
  if flag:
    if sum(op) > count_max:
      count_max = sum(op)

print(count_max)

#!/usr/bin/env python
# coding: utf-8

# In[15]:


N = int(input())
xy_list = []
for _ in range(N):
    A = int(input())
    xy = []
    for _ in range(A):
        xy.append(list(map(int, input().split())))
    xy_list.append(xy)


# In[16]:


ans = 0
for i in range(2**N):
    for j,a_list in enumerate(xy_list):
        if (i>>j)&1 == 1:
            for k,(x,y) in enumerate(a_list):
                if (i>>(x-1))&1 != y:
                    break
            else:
                continue
            break
    else:
        ans = max(ans, bin(i)[2:].count("1"))
print(ans)


# In[ ]:






N = int(input())
testimony = [[-1]*N for i in range(N)]
count = 0
for i in range(N):
  A = int(input())
  for j in range(A):
    x,y = map(int,input().split())
    testimony[i][x-1]=y
for i in range(2**N):
  honest = [0]*N
  for j in range(N):
    if(i>>j)&1:
      honest[j]=1
  flag=True
  for j in range(N):
    if honest[j]==1:
      for k in range(N):
        if testimony[j][k]==-1:
          continue
        if testimony[j][k]!=honest[k]:
          flag=False
  if flag==True:
    count=max(count,honest.count(1))
print(count)

n = int(input())
all_h_or_u = []

#証言リスト
for i in range(n) :
    x = int(input())
    h_or_u = []
    for j in range(x) :
        h_or_u.append(list(map(int, input().split())))
    
    for k in range(x) :
        h_or_u[k][0] -= 1
    
    all_h_or_u.append(h_or_u)
    
#真偽パターン 
all_t_or_f = []
for a in range(2 ** n) :
    t_or_f = []
    for b in range(len(bin(2**n)) - 3) :
        if (a >> b) & 1 :
            t_or_f.append(1)
        else :
            t_or_f.append(0)
        
    all_t_or_f.append(t_or_f)

#真偽パターンに応じた証言の検証
max_cnt = 0
for c in all_t_or_f :
    cnt = 0
    for d in range(n) :
        if c[d] == 1 :
            for e in all_h_or_u[d] :
                if c[e[0]] != e[1] :
                    cnt += 1
    
    if cnt == 0 :
        max_cnt = max(max_cnt, sum(c))
            
print(max_cnt)

N=int(input())

syogen=[]
for i in range(N):
	a=int(input())
	temp=[list(map(int, input().split())) for _ in range(a)]
	syogen.append([a,temp])

ans=0

for h in range(2**N):
	flag=0
	cnt=0
	l=[0]*N
	for g in range(N):
		if h>>g &1:
			l[g]=1
	#print(l)
	for gg in range(N):
		if l[gg]==1:
			temp_=syogen[gg]
			#print(temp_)
			for n in range(temp_[0]):
				if l[temp_[1][n][0]-1]==temp_[1][n][1]:
					continue
				else:
					flag=1
					break
		if flag==1:
			break
		elif flag==0 and gg==N-1:
			#print(bin(h))
			ans=max(ans,sum(l))

print(ans)

n = int(input())
ans, a, l = 0, [], []

for i in range(n):
  a.append(int(input()))
  l.append([])
  for j in range(a[-1]):
    l[i].append(list(map(int,input().split())))

for i in range(2 ** n): #正直者と真偽不明の人がそれぞれ誰なのか全bit探索を使って仮定する
  c, skip = [0] * n, False

  for j in range(n):
    if (i >> j) & 1: c[j] = 1

  for j in range(n):
    if c[j] == 1:
      for k in range(a[j]):
        if c[l[j][k][0]-1] != l[j][k][1]: #正直者の証言と仮定に矛盾が生じた場合
          skip = True
          break
    if skip: break
  else: ans = max(ans, sum(c))

print(ans)

# 不親切な人の証言は、正しかろうが間違っていようが検証できないので無視する
# bit全探索で正直者を仮定・固定して、証言に矛盾が出なければ人数を数えて記録する
from itertools import product
n = int(input())
Ev = [[] for _ in range(n)]

for i in range(n):
    A = int(input())
    for a in range(A):
        x, y = map(int, input().split())
        Ev[i].append((x - 1, y))

bit = list(product([1, 0], repeat=n))

ans = 0
for b in bit:
    for i, v in enumerate(b):  # v == 1 or 0
        if v == 1:
            for x, y in Ev[i]:  # 証言１つ１つを取り出して検証
                if b[x] != y:  # bitで仮定している正直者リストと矛盾する証言を正直者が行ったらアウト
                    break
            else:
                continue
            break
    else:
        ans = max(b.count(1), ans)

print(ans)

n = int(input())
L = []
ans = 0

for i in range(n):
    a = int(input())
    for j in range(a):
        x, y = list(map(int, input().split()))
        L.append((i, x-1, y))

for i in range(1<<n):
    flg = True
    for j, x, y in L:
        if i>>j & 1 and i>>x & 1 != y:
            flg = False
            break
    if flg:
        ans = max(ans, sum(i>>j & 1 for j in range(n)))

print(ans)


N = int(input())
A = [0] * N
x = [0] * N
y = [0] * N
tlist = [0] * N # 1:正直 2:不親切
honest = 0

for i in range(N):
    A[i] = int(input())
    x[i] = []
    y[i] = []
    for j in range(A[i]):
        xt, yt = list(map(int, input().split()))
        x[i].append(xt)
        y[i].append(yt)

for t in range(2**N):
    ns = "0" + str(N) +"b"
    bi = format(t,ns)
    for i in range(N):
        tlist[i] = int(bi[-1-i])
        tflag = True
    for i in range(N):
        for j in range(A[i]):
            if tlist[i] == 1:
                if tlist[x[i][j]-1] != y[i][j]:
                    tflag = False
                    break
        if not tflag:
            break
    if tflag:
        honest = max(honest,sum(tlist))

print(honest)

N = int(input())
testimo_ls = [ [] for i in range(N) ]
rst = 0
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split(' '))
        testimo_ls[i].append([x - 1, y])
for i in range(1 << N):
    honest_ls = []
    for j in range(N):
        if i >> j & 1:
            honest_ls.append(j)
    is_ok_cnt = 0
    is_ok = True
    for s in honest_ls:
        for t in testimo_ls[s]:
            if t[1] == 0 and t[0] in honest_ls:
                is_ok = False
                break
            if t[1] == 1 and t[0] not in honest_ls:
                is_ok = False
                break
    if is_ok:
        rst = max(rst, len(honest_ls))
print(rst)


def resolve():
    N = int(input())
    evdi = [[] for _ in range(N)]
    for i in range(N):
        cnt = int(input())
        for _ in range(cnt):
            x, y = list(map(int, input().split()))
            x -= 1
            evdi[i].append((x, y))

    ans = 0
    for bit in range(1 << N):
        ok = True
        for i in range(N):
            if bit >> i & 1:
                for (x, y) in evdi[i]:
                    if y == 1 and not bit >> x & 1:
                        ok = False
                        break
                    if y == 0 and bit >> x & 1:
                        ok = False
                        break
        cnt = bin(bit).count("1")
        if ok:
            ans = max(cnt, ans)
    print(ans)


def __starting_point():
    resolve()

__starting_point()

#C - HonestOrUnkind2
N = int(input())
A = []
X = []
Y = []
for _ in range(N):
    a = int(input())
    A.append(a)
    box_x = []
    box_y = []
    for _ in range(a):
        x,y = map(int,input().split())
        box_x.append(x)
        box_y.append(y)
    X.append(box_x)
    Y.append(box_y)

person = [2]*N

maxim = 0
for i in range(1<<N):
    c_person = person.copy()
    honest = 0
    for j in range(N):
        mask = 1<<j
        if mask&i != 0:
            c_person[j] = 1
        else:
            c_person[j] = 0
    #正直者かどうかの仮定
    for k,l in enumerate(c_person):
        #kが正直者のとき
        if l == 1:
            #kの証言を判定
            for m,n in zip(X[k],Y[k]):
                #矛盾があるなら honest = 0でbreak
                if c_person[m-1] != n:
                    honest = 0
                    break
            else:
                honest = sum(c_person)
                continue
            break
    maxim = max(maxim,honest)
                
print(maxim)     

import sys
input = sys.stdin.readline

n = int(input())
ans, a, l = 0, [], []

for i in range(n):
  a.append(int(input()))
  l.append([])
  for j in range(a[-1]):
    l[i].append(list(map(int,input().split())))

for i in range(2 ** n): #正直者と真偽不明の人がそれぞれ誰なのか全bit探索を使って仮定する
  c, skip = [0] * n, False

  for j in range(n):
    if (i >> j) & 1: c[j] = 1

  for j in range(n):
    if c[j] == 1:
      for k in range(a[j]):
        if c[l[j][k][0]-1] != l[j][k][1]: #正直者の証言と仮定に矛盾が生じた場合
          skip = True
          break
    if skip: break
  else: ans = max(ans, sum(c))

print(ans)

import itertools
n=int(input())
s=[[] for i in range(n)]
for i in range(n):
  a=int(input())
  for j in range(a):
    x,y=[int(x) for x in input().split()]
    x-=1
    s[i].append([x,y])

l=[]
a=itertools.product(range(2),repeat=n)
for i in a:
  l.append(i)

ans=0
for i in range(2**n):
  c=[]
  for j in range(n):
    if l[i][j]==1:
      for k in s[j]:
        if l[i][k[0]]!=k[1]:
          c.append(False)
  if c==[]:
    ans=max(ans,sum(l[i]))
print(ans)

def main():
	N = int(input())
	A = [[] for i in range(N)]
	# A[i][j] -> i-th person's testimony of person's honesty (j makes no sense)
	for i in range(N):
		a = int(input())
		for j in range(a):
			x, y = [int(b) for b in input().split(" ")]
			A[i].append([x - 1, str(y)])

	cand = []
	for i in range(2 ** N):
		honest_flag = True
		bit = list(pad_zero(format(i, 'b'), N))
		honests = [int(p) for p, q in enumerate(bit) if q == "1"]
		for honest in honests:
			w = A[honest]
			for k in range(len(w)):
				if w[k][1] != bit[w[k][0]]:
					honest_flag = False
		if honest_flag:
			cand.append(len(honests))

	print(max(cand))


def pad_zero(s, n):
	s = str(s)
	return ("0" * n + s)[-n:]

main()

N=int(input())
testimonies=[]

for i in range(N):
  A=int(input())
  testimony=[]
  for j in range(A):
    testimony.append(list(map(int,input().split())))
    testimony[-1][0]-=1
  testimonies.append(testimony)

ans=0
for i in range(2**N):
  isContradiction=False
  for j in range(N):
    if not i&1<<j:continue
    for x,y in testimonies[j]:
      if i&1<<x:x=1
      else:x=0
      if not x==y:
        isContradiction=True
        break
  if not isContradiction:
    ans=max(ans,bin(i).count("1"))
print(ans)

N = int(input())
A = [[] * N for _ in range(N)]
for i in range(N):
    a = int(input())
    for _ in range(a):
        x, y = [int(x) for x in input().split()]
        A[i].append([x - 1, y])

ans = 0
for i in range(1, 1 << N):
    B = format(i, f'0{N}b')[::-1]
    possible = True
    cnt = 0
    for j in range(N):
        if B[j] == '1':
            cnt += 1
            for v in A[j]:
                if v[1] != int(B[v[0]]):
                    possible = False
                    break
    if possible:
        ans = max(ans, cnt)
print(ans)


N=int(input())
XY=[[[]] for n in range(N+1)]
for n in range(1,N+1):
  a=int(input())
  XY[n]=[list(map(int, input().split())) for _ in range(a)]

maxH=0
for mask_i in range(1<<N):
  
  H=[0]*(N+1)
  for n in range(N):
    if mask_i>>n&1:
      H[n+1]=1
  #print(H[1:])
  
  ok=True
  for n in range(1,N+1):
    if H[n]==1:
      for x,y in XY[n]:
        if H[x]!=y:
          ok=False
          break
  if ok:
    maxH=max(maxH,sum(H))

print(maxH)


n = int(input())
ans = 0
al = []
xy = [[] for _ in range(n)]
for k in range(n):
    a = int(input())
    al.append(a)
    for l in range(a):
        x,y = list(map(int,input().split()))
        xy[k].append([x,y])
for i in range(2**n):
    kinds = [0]*n
    jud = 1
    for j in range(n):
        if (i >> j) & 1:
            kinds[j] = 1
    for k in range(n):
        if kinds[k] == 1:
            a = al[k]
            for l in range(a):
                x = xy[k][l][0]
                y = xy[k][l][1]
                if kinds[x-1] != y:
                    jud = 0
    if jud == 1:
        ans = max(ans,kinds.count(1))
print(ans)


# -*- coding: utf-8 -*-

N = int(input())

A = []
data = []
for i in range(N):
    a = int(input())
    A.append(a)
    x = [list(map(int, input().split())) for _ in range(a)]
    data.append(x)

ans = 0
for i in range(1<<N):
    bit = [0] * N
    cnt = 0
    for j in range(N):
        div = 1 << j
        bit[j] = (i // div) % 2
        if bit[j] == 1:
            cnt += 1

    flag = True
    for j in range(N):
        if bit[j] == 0:
            continue
        for a in range(A[j]):
            x = data[j][a]
            if bit[x[0]-1] != x[1]:
                flag = False
                break
        if not flag:
            break
    
    if flag:
        ans = max(ans, cnt)

print(ans)



N = int(input())
testimo_ls = [ [] for i in range(N) ]
rst = 0
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split(' '))
        testimo_ls[i].append([x - 1, y])
for i in range(1 << N):
    honest_ls = []
    for j in range(N):
        if i >> j & 1:
            honest_ls.append(j)
    is_ok = True
    for s in honest_ls:
        for t in testimo_ls[s]:
            if t[0] in honest_ls and t[1] == 0:
                is_ok = False
            if t[0] not in honest_ls and t[1] == 1:
                is_ok = False
    if is_ok:
        rst = max(rst, len(honest_ls))
print(rst)

#
# abc147 c
#
import sys
from io import StringIO
import unittest


class TestClass(unittest.TestCase):
    def assertIO(self, input, output):
        stdout, stdin = sys.stdout, sys.stdin
        sys.stdout, sys.stdin = StringIO(), StringIO(input)
        resolve()
        sys.stdout.seek(0)
        out = sys.stdout.read()[:-1]
        sys.stdout, sys.stdin = stdout, stdin
        self.assertEqual(out, output)

    def test_入力例_1(self):
        input = """3
1
2 1
1
1 1
1
2 0"""
        output = """2"""
        self.assertIO(input, output)

    def test_入力例_2(self):
        input = """3
2
2 1
3 0
2
3 1
1 0
2
1 1
2 0"""
        output = """0"""
        self.assertIO(input, output)

    def test_入力例_3(self):
        input = """2
1
2 0
1
1 0"""
        output = """1"""
        self.assertIO(input, output)


def resolve():
    N = int(input())
    C = []
    for i in range(N):
        a = int(input())
        C.append([list(map(int, input().split())) for j in range(a)])

    ans = 0
    for bit in range(1 << N):
        t = 0
        for i in range(N):
            if bit & (1 << i):
                for c in C[i]:
                    if bit & (1 << c[0]-1) != (1 << c[0]-1)*c[1]:
                        break
                else:
                    t += 1
        if t == bin(bit).count("1"):
            ans = max(ans, t)
    print(ans)


def __starting_point():
     # unittest.main()
     resolve()

__starting_point()

N = int(input())

syougen = [ [] for _ in range(N) ]
for i in range(N):
    num = int(input())
    for j in range(num):
        x, y = map(int, input().split())
        syougen[i].append([x, y])

#print(syougen)
ans = 0
for bit in range(1 << N):
    break_flag = 0
    for i in range(N):
        if (bit >> i) & 1:
            for j in range(len(syougen[i])):
                if ((bit>>(syougen[i][j][0]-1))&1) != syougen[i][j][1]:
                    break_flag = 1
                    break
            if break_flag == 1:
                break
        if i == N-1:
            ans = max(ans, bin(bit).count("1"))
print(ans)

import numpy as np
from itertools import product

N = int(input())
info = []
for i in range(N):
    a = int(input())
    for __ in range(a):
        x,y = list(map(int,input().split()))
        info.append((i,x-1,y))

A = np.array(list(product([0,1], repeat=N)),np.bool)
for i, x, y in info:
    bl = (~A[:,i]) | (A[:,x] == bool(y))
    A = A[bl]
print((A.sum(axis=1).max()))


n=int(input())
a=[]
x=[]
for _ in range(n):
    A=int(input())
    X=[list(map(int,input().split())) for _ in range(A)]
    a.append(A)
    x.append(X)
ans=0

for i in range(2**n):
    tmp=[0]*n
    for j in range(n):
        if (i>>j)&1:
            tmp[j]=1
    for k in range(n):
        if a[k]==0:
            continue
        for h in range(a[k]):
            hito=x[k][h][0]-1
            singi=x[k][h][1]
            if tmp[k]==1:
                if tmp[hito]!=singi:
                    break
        else:
            continue
        break
    else:
        ans=max(ans,sum(tmp))

print(ans)




N = int(input())
A = []
xs = []
ys = []
X = []
Y = []
for i in range(N):
    a = int(input())
    A.append(a)
    for j in range(A[i]):
        x,y = map(int,input().split())
        xs.append(x)
        ys.append(y)
    X.append(xs)
    Y.append(ys)
    xs = []
    ys = []
B = []
ans = 0
count = 0
for i in range(2**N):
    B.append(format(i, 'b'))
for i in range(2**N):
    TF = ["0"]*N
    b = str(B[i])
    for j in range(len(b)):
        TF[-1-j] = b[-1-j]
    for j in range(N):
        if(TF[j] == "1"):
            for k in range(A[j]):
                if(Y[j][k] == 1):
                    if(TF[X[j][k]-1] == "1"):
                        continue
                    else:
                        count += 1
                if(Y[j][k] == 0):
                    if(TF[X[j][k]-1] == "0"):
                        continue
                    else:
                        count += 1
    if(count <= 0):
        ans = max(ans,TF.count("1"))
    count = 0
print(ans)

n=int(input())

syougen=[]
for i in range(n):
    a=int(input())
    
    for _ in range(a):
        x,y = list(map(int,input().split()))
        syougen.append([i,x-1,y])

ans = 0

for bit in range(2**n):
    
    for s in syougen:
        if (bit>>s[0])&1 == 1:
            if (bit>>s[1])&1 != s[2]:
                break
    else:
        thisans = str(bin(bit)).count("1")
        ans=max(ans,thisans)
        # print(bin(bit))
print(ans)


n=int(input())
p=2
from itertools import product
iterator=product(range(p),repeat=n)
#for idxs in iterator:
#    print(idxs)

L=[[] for i in range(n)]
for i in range(n):
    a=int(input())
    for _ in range(a):
        L[i].append(list(map(int,input().split())))
ans=0
for idxs in iterator:
    cnt_honest=0
    for i in range(n):
        cnt=0
        if idxs[i]==1:
            for j in L[i]:
                if idxs[j[0]-1]==j[1]:
                    cnt+=1
            if cnt==len(L[i]):
                cnt_honest+=1
    if cnt_honest==sum(idxs):
        ans=max(sum(idxs),ans)
print(ans)

n = int(input())
xy = [[] for i in range(n)]
for i in range(n):
    a = int(input())
    for j in range(a):
        x,y = map(int, input().split())
        xy[i].append((x,y))

ans = 0
for i in range(2**n):
    isOk = True
    res = []
    cnt = 0
    for j in range(n) :
        x = i >> j & 1
        res.append(x)
    for j in range(n):
        x = i >> j & 1
        if(x):
            cnt += 1
            for v in xy[j] :
                x,y = v
                x -= 1
                if(res[x] != y):
                    isOk = False
    if(isOk):
        ans = max(ans, cnt)  
print(ans)

N = int(input())
a = [0] * N
xy = [[]] * N
for i in range(N):
    a[i] = int(input())
    xy[i] = [list(map(int, input().split())) for _ in range(a[i])]
# print(xy)
ans = 0
for i in range(2 ** N):
    tf = [False] * N
    for j in range(N):
        if (i >> j) & 1:
            tf[j] = True
    flag = False
    for j in range(N):
        for k in xy[j]:
            # 正直者が嘘をついたことになれば矛盾している
            if tf[j] and k[1] != tf[k[0] - 1]:
                flag = True
                break
        if flag:
            break
    if flag:
        continue
    ans = max(ans, tf.count(True))
print(ans)


N = int(input())

mastar_list = []
for i in range(2 ** N):
    x = "{:0" + str(N) + "b}"
    mastar_list.append(list(map(int,x.format(i))))


current = 1
ans = []
judge = [True for i in range(2 ** N)]
while current <= N:
    now = current -1
    loop_num = int(input())
    for i in range(loop_num):
        a,b = list(map(int,input().split()))
        c = a - 1
        for index, situation in enumerate(mastar_list):
            if situation[now] == 1:
                if situation[c] == b:
                    pass
                else:
                    judge[index] = False
            else:
                pass
    current += 1

ans = []
for index, content in enumerate(judge):
    if content:
        ans.append(sum(mastar_list[index]))
        
print((max(ans)))


n = int(input())
m = []
a = [[] for i in range(n)]
for i in range(n):
    tmp = int(input())
    m.append(tmp)
    for j in range(tmp):
        a[i].append(list(map(int,input().split())))

ans = 0

for i in range(2**n):
    cnt = 0
    for j in range(n):
        flg = True
        if i >> j & 1:
            cnt += 1
            for k in range(m[j]):
                kj = (i >> (a[j][k][0]-1)) & 1
                if a[j][k][1] != kj:
                    flg = False
                    break
            if not flg:
                break
    if flg:
        ans = max(ans, cnt)

print(ans)  


n = int(input())
t = [[-1]*n for _ in range(n)]
ans = 0
for i in range(n):
  a = int(input())
  for j in range(a):
    x,y = map(int, input().split())
    t[i][x-1] = y
for i in range(2**n):
  h = [0]*n
  for j in range(n):
    if i >> j & 1:
      h[j] = 1
  f = 1
  for k in range(n):
    if h[k]:
      for l in range(n):
        if t[k][l] == -1:
          continue
        if t[k][l] != h[l]:
          f = 0
  if f:
    ans = max(ans,h.count(1))
print(ans)

from sys import stdin, stdout # only need for big input

max_honest = 0
testomonies = []
state = []

def dfs(person):
    nonlocal max_honest
    if person >= len(state):
        correctState = True
        for p in range(len(state)):
            if state[p] == 1:
                for t in testomonies[p]:
                    x, y = t
                    if state[x] != y:
                        correctState = False
                        break
        if correctState:
            sum = 0
            for s in state:
                sum += s
            max_honest = max(max_honest, sum)
        return

    state[person] = 0
    dfs(person + 1)

    state[person] = 1 
    dfs(person + 1)
    

def solve():
    nonlocal state
    n = int(stdin.readline())
    for _ in range(n):
        a = int(stdin.readline())
        t = []
        for _ in range(a):
            x, y = [int(inp) for inp in stdin.readline().split()]
            t.append((x - 1,y))
        testomonies.append(t)
    # print(testomonies)
    state = [-1] * n
    dfs(0)
    print(max_honest)


def main():
    solve()


def __starting_point():
    main()
__starting_point()

n = int(input())
g = [[-1 for _ in range(15)] for _ in range(15)]
for i in range(n):
  a = int(input())
  for j in range(a):
    x, y = map(int, input().split())
    g[i][x-1] = y
    
ans = 0
for bit in range(1<<n):
  honests = [0]*n
  for i in range(n):
    if bit & 1<<i: honests[i] = 1
  flg = True
  for i in range(n):
    if honests[i]:
      for j in range(n):
        if g[i][j] == -1: continue
        if g[i][j] != honests[j]: flg = False
  if flg:
    ans = max(ans, honests.count(1))
print(ans)

from itertools import product

n = int(input())
info = {}
for p in range(n):
    a = int(input())
    L = []
    for _ in range(a):
        x,y = list(map(int, input().split()))
        x,y = x-1, y
        L.append((x,y))
    info[p] = L

ans = 0
for bit_pattern in product(range(2), repeat=n):
    for p,bit in enumerate(bit_pattern):
        if bit:
            if not all([bit_pattern[x] == y for x,y in info[p]]):
                break
    else:
        ans = max(ans, sum(bit_pattern))

print(ans)

n=int(input())
say=[]
for i  in range(n):
    qq=[]
    for i in range(int(input())):
        qq.append(list(map(int,input().split())))
    say.append(qq)
ans=0
for bit in range(1<<n):
    plate=0
    L=[(bit>>i)&1 for i in range(n)]
    for i in range(n):
        if L[i]==0:continue
        for l in say[i]:
            if  L[l[0]-1] != l[1]:
                plate=1;break
        if plate:break
    else:
        ans=max(ans,sum(L))
print(ans)

n=int(input())
a=[]
x=[]
for _ in range(n):
    A=int(input())
    X=[list(map(int,input().split())) for _ in range(A)]
    a.append(A)
    x.append(X)
ans=0

for i in range(2**n):
    tmp=[0]*n
    for j in range(n):
        if (i>>j)&1:
            tmp[j]=1
    for k in range(n):
        # if a[k]==0:
        #     continue
        for h in range(a[k]):
            hito=x[k][h][0]-1
            singi=x[k][h][1]
            if tmp[k]==1:
                if tmp[hito]!=singi:
                    break
        else:
            continue
        break
    else:
        ans=max(ans,sum(tmp))

print(ans)




def digitSum(n):
    s = str(bin(n))
    s = s[2:]
    array = list(map(int, s))
    return sum(array)
N = int(input())
A = []
X = []
Y = []
res = 0
for i in range(N):
    a = int(input())
    A.append(a)
    X_temp = []
    Y_temp = []
    for j in range(a):
        x,y = map(int,input().split())
        X_temp.append(x)
        Y_temp.append(y)
    X.append(X_temp)
    Y.append(Y_temp)
for i in range(1 << N):
    judge = True
    for j in range(N):
        if (i >> j) & 1:#もしAjが正直者だったら
            for k in range(A[j]):
                if (i >> X[j][k]-1) & 1 != Y[j][k]:
                    judge = False
        """else:#もしAjが不親切ものだったら。不親切者も正しいことをいうこともある。
            for k in range(A[j]):#
                if (i >> X[j][k]-1) & 1 == Y[j][k]:
                    judge = False"""
    if judge:
        res = max(res,digitSum(i))
print(res)

n = int(input())
statement = [[] for _ in range(n)]


for i in range(n):
    A = int(input())
    for j in range(A):
        x, y = list(map(int, input().split()))
        if y == 1:
            statement[i].append([x-1, True])
        if y == 0:
            statement[i].append([x-1, False])

cnt = 0
for bit in range(2**n):
    honest = []
    for i in range(n):
        if (bit >> i) & 1:
            honest.append(i)
    flag = True
    for j in range(len(statement)):
        if j in honest:
            for k in honest:
                if [j, False] in statement[k]:
                    flag = False
                    break
        else:
            for k in honest:
                if [j, True] in statement[k]:
                    flag = False
                    break
        
        if not flag:
            break  
    if flag:
        cnt = max(cnt, len(honest))
print(cnt)


n=int(input())

comment=[]
for i in range(n):
    a=int(input())
    
    for _ in range(a):
        x,y = list(map(int,input().split()))
        comment.append([i,x-1,y])

ans = 0

for bit in range(2**n):
    
    for s in comment:
        if (bit>>s[0])&1 == 1:
            if (bit>>s[1])&1 != s[2]:
                break
    else:
        tmp = str(bin(bit)).count("1")
        ans=max(ans,tmp)
print(ans)


N=int(input())
testimony=[[-1]*N for i in range(N)]
count=0
for i in range(N):
    A=int(input())
    for j in range(A):
        x,y=map(int,input().split())
        testimony[i][x-1]=y
for i in range(1<<N):
    honest=[0]*N
    for j in range(N):
        if (i>>j)&1:
            honest[j]=1
    flag=True
    for j in range(N):
        if honest[j]:
            for k in range(N):
                if testimony[j][k]==-1:
                    continue
                if testimony[j][k]!=honest[k]:
                    flag=False
    if flag:
        count=max(count,honest.count(1))
print(count)

import sys
from io import StringIO
import unittest
import itertools

def yn(b):
    print("Yes" if b==1 else "No")
    return

def resolve():
    readline=sys.stdin.readline
    n=int(readline())
    dat = [[-1 for i in range(n)] for j in range(n)]
    for i in range(n):
        m=int(readline())
        for j in range(m):
            x,y=map(int, readline().rstrip().split())
            x-=1
            dat[i][x] = y
    
    ans=0
    for ptn in itertools.product([False,True], repeat=n):
        ok=True
        for i in range(n):
            if ptn[i]==False:
                continue
            for j in range(n):
                if dat[i][j] == -1:
                    continue
                if dat[i][j] == 1 and ptn[j]==False:
                    ok=False
                    break
                if dat[i][j] == 0 and ptn[j]==True:
                    ok=False
                    break
            if ok==False:
                break
        if ok==True:
            ans=max(ans,ptn.count(True))
    print(ans)

    return

if 'doTest' not in globals():
    resolve()
    return

n = int(input())
li = [[-1 for _ in range(n)] for _ in range(n)]
for i in range(n):
    a = int(input())
    for j in range(a):
        x, y = map(int, input().split())
        li[i][x-1] = y

ans = 0
for i in range(2**n):
    s = 0
    t = [0]*n
    for j in range(n):
        if i>>j & 1:
            t[j]=1
    is_contradict = 0
    for j in range(n):
        if t[j]:
            for k in range(n):
                if li[j][k]==-1:
                    continue
                if li[j][k] != t[k]:
                    is_contradict = 1
    if not is_contradict:
        ans = max(ans, sum(t))

print(ans)

from itertools import product

n = int(input())

test = []

for i in range(n):
  a = int(input())
  test.append([list(map(int, input().split())) for i in range(a)])

ans = 0

for i in product(range(2), repeat=n):
  flag = True
  for j in range(n):
    if i[j] == 1:
      for s in test[j]:
        if i[s[0]-1] != s[1]:
          flag = False 
          break
  if flag == True:
    cnt = i.count(1)
    if cnt > ans:
      ans = cnt

print(ans)

N = int(input())

W = [[-1]*N for _ in range(N)]
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = [int(z) for z in input().split()]
        x -= 1
        W[i][x] = y

M = 0
for b in range(2**N):

    d = [0] * N
    for i in range(N):
        if (b >> i) & 1:
            d[i] = 1
    
    ok = True
    for i in range(N):
        if d[i] == 1:
            for j in range(N):
                if W[i][j] == -1:
                    continue
                if W[i][j] != d[j]:
                    ok =False

    if ok == True:
        M = max(M, sum(d))

print(M)

N = int(input())
A = []
XY = []
for i in range(N):
    a = int(input())
    A.append(a)
    xy = [list(map(int,input().split())) for j in range(a)]
    XY.append(xy)
ans = 0
for i in range(2**N):
    b = [i>>j&1 for j in range(N)]
    f = 0
    for j in range(N):
        if b[j] == 1:
            for k in range(A[j]):
                x = XY[j][k][0] -1
                y = XY[j][k][1]
                if b[x] != y:
                    f = 1
                    break
        if f:
            break
    else:
        ans = max(ans,b.count(1))
print(ans)

from itertools import product

n = int(input())

d = {}
for i in range(n):
  a = int(input())
  for _ in range(a):
    x, y = map(int, input().split())
    if i + 1 not in d:
      d[i + 1] = []
    d[i + 1].append((x, y))

ret = 0
for x in product((0, 1), repeat=n):
  tmp = [-1] * n
  ok = True
  for i in range(n):
    if x[i] == 1 and i + 1 in d:
      for y in d[i + 1]:
        if tmp[y[0] - 1] == -1:
          tmp[y[0] - 1] = y[1]
        elif tmp[y[0] - 1] != y[1]:
          ok = False
          break
    if not ok:
      break
  if ok and all(a == b or b == -1 for a, b in zip(x, tmp)):
    ret = max(ret, sum(x))

print(ret)

n = int(input())
a = []
xy = [[] for i in range(n)]
for i in range(n):
    a.append(int(input()))
    for j in range(a[i]):
        xy[i].append(list(map(int, input().split())))
ans = 0
for i in range(2**n):
    tf = [False for j in range(n)]
    for j in range(n):
        if (i>>j)&1:
            tf[j] = True
    flag = False
    for j in range(n):
        for k in range(a[j]):
            if tf[j]:
                if xy[j][k][1] != tf[xy[j][k][0]-1]:
                    flag = True
                    break
        if flag:
            break
    else:
        ans = max(ans, tf.count(True))
print(ans)

N=int(input())
Alist=[]
xylists=[]
for i in range(N):
    A=int(input())
    Alist.append(A)
    xylist=[]
    for j in range(A):
        xylist.append(tuple(map(int,input().split())))
    xylists.append(xylist)
ans=0
for bit in range(1<<N):
    HOU=list(reversed(list(format(bit,'b').zfill(N))))
    #print(HOU)
    notans=False
    for i in range(N):
        if bit&(1<<i):
            for x,y in xylists[i]:
                if HOU[x-1]!=str(y):
                    notans=True
                    #print(bit)
                    break #not ans
            else:
                continue
            break
        else:
            continue
        break
    #print(bit,HOU,notans)
    if not notans:
        ans=max(ans,str(bin(bit)).count('1'))
print(ans)

N = int(input())
testimony = []
for i in range(N):
    A = int(input())
    testimony.append([-1]*N)
    for i in range(A):
        x, y = map(int, input().split())
        testimony[-1][x-1] = y

ans = 0
for i in range(2**N):
    total = 0
    tmplst = [0]*N
    for j in range(N):
        if ((i >> j) & 1):
            tmplst[j] = 1

    ch = 0
    for j in range(N):
        if tmplst[j] == 1:
            for a, b in zip(testimony[j], tmplst):
                if (a == 1 and b == 0) or (a == 0 and b == 1):
                    ch = 1
                    break
            
            if ch == 1:
                break

    if ch == 0:
        if ans < sum(tmplst):
            ans = sum(tmplst)

print(ans)



n = int(input())
li = []
for i in range(n):
    a = int(input())
    subli = []
    for j in range(a):
        x, y = list(map(int, input().split()))
        subli.append([x, y])
    li.append(subli)

ans = 0

for i in range(2 ** n):
    tf = [False] * n
    out = False
    for j in range(n):
        if ((i >> j) & 1):
            tf[j] = True
    for k in range(len(li)):
        if (tf[k] == True):
            for l in li[k]:
                if not(l[1] == tf[l[0]-1]):
                    out = True
    if not (out):
        ans = max(ans, tf.count(True))

print(ans)


N = int(input())
testimo_ls = [ [] for i in range(N) ]
rst = 0
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split(' '))
        testimo_ls[i].append([x - 1, y])
for i in range(1 << N):
    honest_ls = []
    for j in range(N):
        if i >> j & 1:
            honest_ls.append(j)
    is_ok = True
    for s in honest_ls:
        for t in testimo_ls[s]:
            if t[0] not in honest_ls and t[1] == 1:
                is_ok = False
                break
            if t[0] in honest_ls and t[1] == 0:
                is_ok = False
                break
    if is_ok:
        rst = max(rst, len(honest_ls))
print(rst)

N = int(input())

hatsugen = [[] for _ in range(N)]
#print(hatsugen)
A = -1
while True:
  try:
  	s = input()
  except EOFError:
    break  
  a = tuple(map(int,s.rstrip().split()))
  #print(a)
  if len(a) == 1:
    A += 1
  else:
    hatsugen[A].append(a)
#print(hatsugen)

ans = 0
for i in range(2**N):
  
  bit = i
  flag = [0]*N
  idx = 0
  while bit:
    if (bit&1):
      flag[idx] = 1
    bit >>= 1
    idx+=1
  
  flag2=0
  #print(flag)
  for i in range(N):
    if flag[i]:
      hatsu = hatsugen[i]
    else:
      continue
    for word in hatsu:
      #print(*word)
      if flag[word[0]-1] != word[1]:
        flag2 = 1
        #print("false")
        break
    if flag2:
      break
  if flag2==0:
    ans = max(ans, sum(flag))

print(ans)
    
  
      


n=int(input())
a=[]
x=[]
for _ in range(n):
    A=int(input())
    X=[list(map(int,input().split())) for _ in range(A)]
    a.append(A)
    x.append(X)
ans=0

for i in range(2**n):
    tmp=[0]*n
    for j in range(n):
        if (i>>j)&1:
            tmp[j]=1
    for k in range(n):
        for h in range(a[k]):
            hito=x[k][h][0]-1
            singi=x[k][h][1]
            if tmp[k]==1:
                if tmp[hito]!=singi:
                    break
        else:
            continue
        break # https://note.nkmk.me/python-break-nested-loops/
    else:
        ans=max(ans,sum(tmp))

print(ans)

n = int(input())

statements = []

for i in range(n):
    a = int(input())
    astates = [list(map(int, input().split())) for _ in range(a)]

    statements.append(astates)

cnt = 0
for i in range(2**n):
    state = format(i, "0"+str(n)+"b")

    pos = True
    for j in range(n):
        if state[j] == "1":
            for x, y in statements[j]:
                if not (state[x-1] == str(y)):
                    pos = False
                    break

        if not pos:
            break

    if pos:
        cnt = max(cnt, state.count("1"))

print(cnt)

N = int(input())
xy = [[] for i in range(N)]
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split())
        xy[i].append([x, y])

ans = 0

for i in range(2**N):
    b = format(i, "0" + str(N) + "b")
    t = 0
    f = 0
    for j in range(N):
        if b[j] == "1":
            t += 1
            for k in xy[j]:
                if str(k[1]) != b[k[0]-1]:
                    f = 1
                    break
    if f == 0:
        ans = max(ans, t)
        #print(b)

print(ans)

from itertools import product

n = int(input())
data = {}
for p in range(1, n+1):
    a = int(input())
    # 人p=1～の証言
    data[p] = [list(map(int, input().split())) for _ in range(a)]
    
# パターン生成
ans = 0
for honest in product(range(2), repeat=n):
    for p,hk in enumerate(honest, 1):
        if hk == 1:
            # 証言の矛盾をチェック
            if not all([honest[x-1] == y for x,y in data[p]]):
                break
    else:
        ans = max(ans, sum(honest))

print(ans)

n=int(input())
a=[]
l=[]
for i in range(n):     
      A=int(input())
      L=[list(map(int,input().split())) for _ in range(A)]
      a.append(A)
      l.append(L)
ans=0
for i in range(2**n):
      b=[0]*n
      for j in range(n):
            if (i>>j)&1:
                  b[j]=1
      for k in range(n):
            for h in range(a[k]):
                  hito=l[k][h][0]-1
                  singi=l[k][h][1]
                  if b[k]==1 and b[hito]!=singi:
                        break      
            else:
                  continue
            break
      else:
            ans=max(ans,sum(b))

print(ans)
                  


n = int(input())

xy = [[] for _ in range(n)]
for i in range(n):
    a = int(input())
    xy[i] = [[int(i) for i in input().split()] for _ in range(a)]

ans = 0
for i in range(2**n):
    lst = [0 for _ in range(n)]
    for j in range(n):
        if (i >> j) & 1:
            lst[j] = 1
    
    flag = True
    for j in range(n):
        if lst[j] == 1:
            for x, y in xy[j]:
                if lst[x - 1] != y:
                    flag = False
                    break
            else:
                continue
            break

    if flag:
        ans = max(ans, sum(lst))
print(ans)

n = int(input())
Dup = []

for i in range(n):
    a = int(input())
    Dup.append([])
    for j in range(a):
        x,y = map(int, input().split())
        Dup[-1].append((x-1,y))

def is_honest (i,j):
    return (i >> j)%2 == 1

def honest_cnt(i):
    ans = 0
    for j in range(n):
        ans += is_honest(i,j)
    return ans

ans = 0

for i in range(1 << n):
    ok = True
    for j in range(n):
        if not is_honest(i,j):continue

        for x,y in Dup[j]:
            if y == 0 and is_honest(i,x): ok = False
            if y == 1 and not is_honest(i,x): ok = False

    if ok:
        ans = max(ans,honest_cnt(i))

print(ans)

# 全探索

n=int(input())

class People:
    def __init__(self):
        self.type=None

peoples=[People() for i in range(n+1)]

def change_10to2(i):
    ans=format(i, '#0' + str(n + 3) + 'b')[2:]
    return ans

def set_people_type(binary_list,peoples):
    for i,people in enumerate(peoples):
        if i!=0:
            people.type=binary_list[i]

def get_statement():
    shougen={}
    for i in range(1,n+1):
        ai=int(input())
        ans=[]
        for j in range(ai):
            kumi=[int(k) for k in input().split()]
            ans.append(kumi)
        shougen[str(i)]=ans
    return shougen

shougens=get_statement()

def shougen_dicide(peoples,shougens):
    for i in range(1,n+1):
        shougen=shougens[str(i)]
        for shou in shougen:
            people,type=shou
            people=int(people)
            type=str(type)
            # 正直者のとき
            if peoples[i].type=="1":
                if peoples[people].type!=type:
                    return False

            # #嘘つきのとき
            # else:
            #     if peoples[people].type==type:
            #         return False
    return True



ans=0
for i in range(2**n):
    binary_list=change_10to2(i)
    set_people_type(binary_list,peoples)
    if shougen_dicide(peoples,shougens):
        ans=max(ans,binary_list.count("1"))
print(ans)


n = int(input())
g = [[-1 for _ in range(15)] for _ in range(15)]
for i in range(n):
  a = int(input())
  for j in range(a):
    x, y = map(int, input().split())
    g[i][x-1] = y
    
ans = 0
for bit in range(1<<n):
  honests = [0]*n
  for i in range(n):
    if bit & 1<<i: honests[i] = 1
  flg = True
  for i in range(n):
    if honests[i]:
      for j in range(n):
        if g[i][j] == -1: continue
        if g[i][j] != honests[j]: flg = False
  if flg:
    ans = max(ans, honests.count(1))
print(ans)

n = int(input())
lista = []
xy = []
for i in range(n):
    a = int(input())
    lista.append(a)
    s = [list(map(int, input().split())) for _ in range(a)]
    xy.append(s)
ans = 0
for j in range(2**n):
    num = 0
    d = []
    for k in range(n):
        if((j >> k) & 1) == 1:
            d.append(1)
        else:
            d.append(0)
    c = 0
    for l in range(n):
        cnt = 0
        if d[l] == 1:
            if lista[l] != 0:
                for m in range(lista[l]):
                    if xy[l][m][1] == d[xy[l][m][0] - 1]:
                        cnt += 1
                        if cnt == lista[l]:
                            c += 1
                    else:
                        break
            else:
                c += 1
    if c == d.count(1):
        num = c
    ans = max(num, ans)
print(ans)

#!/usr/bin/env python3
import sys
from itertools import chain
from itertools import product


def check(N, ptn, m_assert):
    for i in range(N):
        if ptn[i] == 1:
            for j in range(i + 1, N):
                if ptn[j] == 1:
                    if m_assert[i][j] == 0:
                        return False
                    if m_assert[j][i] == 0:
                        return False
                else:
                    if m_assert[i][j] == 1:
                        return False
        else:
            for j in range(i + 1, N):
                if ptn[j] == 1:
                    if m_assert[j][i] == 1:
                        return False
    return True


def solve(N, m_assert):
    ans = 0
    for ptn in product([1, 0], repeat=N):
        if check(N, ptn, m_assert):
            ans = max(sum(ptn), ans)
    return ans


def main():
    N = int(input())
    m_assert = [[-1] * N for _ in range(N)]
    for n in range(N):
        A = int(input())
        for a in range(A):
            x, y = list(map(int, input().split()))
            m_assert[n][x - 1] = y
    answer = solve(N, m_assert)
    print(answer)


def __starting_point():
    main()

__starting_point()

n = int(input())
al, xyl = [], []
for _ in range(n):
    a = int(input())
    xy = [list(map(int, input().split())) for _ in range(a)]
    xyl.append(xy)

ans = 0
for i in range(2**n):
    cnt = 0
    flag = True
    for j in range(n):
        if (i >> j) & 1:
            cnt += 1
            for x, y in xyl[j]:
                x -= 1
                if (i >> x) & 1 != y:
                    flag = False
    if flag:
        ans = max(ans, cnt)
print(ans)

def resolve():
    N = int(input())
    evdi = [[] for _ in range(N)]
    for i in range(N):
        cnt = int(input())
        for _ in range(cnt):
            x, y = list(map(int, input().split()))
            x -= 1
            evdi[i].append((x, y))

    ans = 0
    for bit in range(1 << N):
        ok = True
        for i in range(N):
            if bit >> i & 1:
                for (x, y) in evdi[i]:
                    if y == 1 and not bit >> x & 1:
                        ok = False
                        break
                    if y == 0 and bit >> x & 1:
                        ok = False
                        break
        cnt = bin(bit).count("1")
        if ok:
            ans = max(cnt, ans)
    print(ans)


def __starting_point():
    resolve()

__starting_point()

import sys
import math
import itertools
from collections import defaultdict, deque, Counter
from copy import deepcopy
from bisect import bisect, bisect_right, bisect_left
from heapq import heapify, heappop, heappush
    
input = sys.stdin.readline
def RD(): return input().rstrip()
def F(): return float(input().rstrip())
def I(): return int(input().rstrip())
def MI(): return map(int, input().split())
def MF(): return map(float,input().split())
def LI(): return list(map(int, input().split()))
def TI(): return tuple(map(int, input().split()))
def LF(): return list(map(float,input().split()))
def Init(H, W, num): return [[num for i in range(W)] for j in range(H)]

def main():
    N = I()
    D = [[[],[]] for i in range(N)]
    for i in range(N):
        a = I()
        for j in range(a):
            x, y = MI()
            if y == 1:
                D[i][0].append(x-1)
            else:
                D[i][1].append(x-1)
    visit = [0]*N
    res = 0
    
    A = [0,1]
    for i in itertools.product(A, repeat=N):
        ans = True
        for index, j in enumerate(i):
            if j == 0:
                continue
            else:
                for k in D[index][0]:
                    if i[k] == 0:
                        ans = False
                        break
                for k in D[index][1]:
                    if i[k] == 1:
                        ans = False
                        break
        if ans:
            res = max(res, sum(i))
    print(res)

def __starting_point():
    main()
__starting_point()

import copy
N = int(input())
testimony = []
for n in range(N):
    A = int(input())
    testimony.append({})
    for a in range(A):
        x, y = map(int, input().split())
        testimony[n][x - 1] = y    

def judge(truthy):
    answer = True
    for i in range(len(truthy)):
        if truthy[i] == 1:
            for t in testimony[i].keys():
                if truthy[t] != testimony[i][t]:
                    answer = False
                    break
        if not answer:
            break
    # print(answer, truthy)
    return 0 if not answer else truthy.count(1)

def dfs(truthy, depth):
    if N == depth:
        return judge(truthy)
    truth = copy.copy(truthy)
    truth.append(1)
    t = dfs(truth, depth + 1)
    false = copy.copy(truthy)
    false.append(0)
    f = dfs(false, depth + 1)
    return max(t, f)

print(dfs([], 0))

def HonestOrUnkind2():
    n = int(input())
    lang = [[-1]*n for _ in range(n)]
    ans = 0
    
    for i in range(n):
        a = int(input())
        for _ in range(a):
            x, y = list(map(int, input().split()))
            lang[i][x-1] = y

    # 2分全探索
    for i in range(2**n):
        status = [0 for _ in range(n)]
        for j in range(n):
            if (i>>j)&1:
                status[j] = 1
        ans0 = True
        for j in range(n):
            if status[j] == 1:
                for k in range(n):
                    if lang[j][k] == -1:
                        continue
                    if lang[j][k] != status[k]:
                        ans0 = False
        if ans0:
            ans = max(ans, status.count(1))
    print(ans)
                    
                
def __starting_point():
    HonestOrUnkind2()
    

__starting_point()

N=int(input())
T=[[] for _ in range(N)]
for i in range(N):
  n=int(input())
  for j in range(n):
    T[i].append(tuple(map(int,input().split())))
ans=0
for i in range(2**N):
  true,t,f=set(),set(),set()
  for j in range(N):
    if i>>j&1:
      true.add(j+1)
      for a,b in T[j]:
        if b:
          t.add(a)
        else:
          f.add(a)
  if t<=true and not(f&true):
    ans=max(ans,len(true))
print(ans)

n=int(input())
xy=[[[]] for _ in range(n)]
for i in range(n):
    a=int(input())
    xy[i]=[list(map(int,input().split())) for _ in range(a)]
ans=0
for i in range(2**n):
    tmp=[0]*n
    flag1=True
    for j in range(n):
        if (i>>j)&1:
            tmp[j]=1
    for k in range(n):
        flag2=True
        if tmp[k]==1:
            for x,y in xy[k]:
                if tmp[x-1]!=y:
                    flag1=False
                    flag2=False
                    break
        if not flag2:
            break
    if flag1:
        ans=max(ans,sum(tmp))
print(ans)

# -*- coding: utf-8 -*-
"""
Created on Sun Sep 13 02:01:40 2020

@author: liang
"""

N = int(input())
A = list()
T = [list() for i in range(N)]

#データ挿入
for i in range(N):
    a = int(input())
    A.append(a)
    for a in range(a):
        x, y = list(map(int,input().split()))
        x -= 1 #配列のインデックスに対応
        T[i].append((x,y))
ans = 0
#bit全探索
for i in range(2**N):
    #正直者のインデックスを格納
    persons = list()
    for j in range(N):
        if i>>j&1 == 1:
            persons.append(j)
    #正直者　= True
    d = [False]*N
    for p in persons:
        d[p] = True 

    judged = [False]*N
    #全ての人に対してループ
    for num in range(N):
        #正直者のみ採用
        f = False
        if d[num]:
            for t in T[num]:
                x, y = t[0], t[1]
                #dのテーブルを更新
                if y == 1 and d[x] != True:
                    f = True
                    break
                if y == 0 and d[x] != False:
                    f = True
                    break
        if f:
            break
    else:
        #print(d)
        ans = max(ans, len(persons))
print(ans)


N = int(input())
testimo_ls = [ [] for i in range(N) ]
rst = 0
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split(' '))
        testimo_ls[i].append([x - 1, y])
for i in range(1 << N):
    honest_ls = []
    for j in range(N):
        if i >> j & 1:
            honest_ls.append(j)
    is_ok = True
    for s in honest_ls:
        for t in testimo_ls[s]:
            if t[0] in honest_ls and t[1] == 0:
                is_ok = False
                break
            if t[0] not in honest_ls and t[1] == 1:
                is_ok = False
                break
    if is_ok:
        rst = max(rst, len(honest_ls))
print(rst)

N = int(input())
testimo_ls = [ [] for i in range(N) ]
rst = 0
for i in range(N):
    A = int(input())
    for j in range(A):
        x, y = map(int, input().split(' '))
        testimo_ls[i].append([x - 1, y])
for i in range(1 << N):
    honest_ls = []
    for j in range(N):
        if i >> j & 1:
            honest_ls.append(j)
    is_ok = True
    for s in honest_ls:
        for t in testimo_ls[s]:
            if t[1] == 0 and t[0] in honest_ls:
                is_ok = False
                break
            if t[1] == 1 and t[0] not in honest_ls:
                is_ok = False
                break
    if is_ok:
        rst = max(rst, len(honest_ls))
print(rst)

N = int(input())
xy = [[] for _ in range(N)]

for i in range(N):
  A = int(input())
  for _ in range(A):
    xy[i].append(list(map(int, input().split())))
lst = [[0 for j in range(N)] for k in range(2**N)]

for l in range(2**N):
  for m in range(N):
    if (l >> m) & 1:
      lst[l][m] = 1

ans = 0
for n in lst:
  flag = True
  for f in range(N):
    if n[f] == 1:
      for g in xy[f]:
        if n[g[0]-1] != g[1]:
          flag = False
          break
    else:
      tmp = 0
      for g in xy[f]:
        if n[g[0]-1] == g[1]:
          tmp += 1
      if tmp == len(n):
        flag = False
    if not flag:
      break
  if flag:
    ans = max(ans, n.count(1))
print(ans)

#!/usr/bin/env python

# input
n = int(input())
a = [0 for _ in range(n)]
x = [[] for _ in range(n)]
y = [[] for _ in range(n)]
for i in range(n):
    a[i] = int(input())
    for _ in range(a[i]):
        x_, y_ = list(map(int, input().split()))
        x_ -= 1
        x[i].append(x_)
        y[i].append(y_)

# calc
# Full search
max_honest = 0 
for i in range(2**n):
    s = []
    tmp = i 
    for _ in range(n):
        s.append(tmp%2)
        tmp //= 2
    s = list(reversed(s))
    honest = sum(s)
    
    ok = True
    for j in range(n):
        for k in range(a[j]):
            if s[j] == 1 and s[x[j][k]] != y[j][k]:
                #print('######')
                #print('x[{}][{}] = {}'.format(j, k, x[j][k]))
                #print('y[{}][{}] = {}'.format(j, k, y[j][k]))
                #print('s[x[{}][{}]] = {}'.format(j, k, s[x[j][k]]))
                ok = False
                break
        if not ok: 
            break

    if ok: 
        if max_honest <= honest:
            max_honest = honest

print(max_honest)


n = int(input())
graph = [[-1 for _ in range(n)] for _ in range(n)]
for i in range(n):
    a = int(input())
    for _ in range(a):
        x, y = map(int, input().split())
        graph[i][x-1] = y

ans = 0
for p in range(2**n):
    q = p
    c = 0
    t = []
    l = 0
    while q:
        if q&1:
            t.append(graph[c])
            l += 1
        q >>= 1
        c += 1
    flag = True
    for c in range(n):
        if p&1:
            for s in t:
                if s[c] == 0:
                    flag = False
        else:
            for s in t:
                if s[c] == 1:
                    flag = False
        p >>= 1
    if flag:
        ans = max(ans, l)

print(ans)

N = int(input())
ls1 = []
for i in range(N):
    A = int(input())
    ls2 = []
    for i in range(A):
        x, y = map(int,input().split())
        ls2.append([x,y])
    ls1.append(ls2)
ans = 0
f = True
for i in range(2**N):
    for j in range(N):
        if (i>>j&1):
            f = True
            for k in ls1[j]:
                if (i >>(k[0] - 1) &1) == (k[1]&1):
                    continue
                else:
                    f = False
                    break
            if f == False:
                break
    if f:
        ans = max(ans,bin(i).count('1'))    
print(ans)

from sys import stdin, stdout # only need for big input

max_honest = 0
testomonies = []
state = []

def dfs(person):
    nonlocal max_honest
    if person >= len(state):
        correctState = True
        for p in range(len(state)):
            if state[p] == 1:
                for t in testomonies[p]:
                    x, y = t
                    if state[x] != y:
                        correctState = False
                        break
        if correctState:
            sum = 0
            for s in state:
                sum += s
            max_honest = max(max_honest, sum)
        return

    state[person] = 0
    dfs(person + 1)

    state[person] = 1 
    dfs(person + 1)
    

def solve():
    nonlocal state
    n = int(input())
    for _ in range(n):
        a = int(input())
        t = []
        for _ in range(a):
            x, y = [int(inp) for inp in input().split()]
            t.append((x - 1,y))
        testomonies.append(t)
    # print(testomonies)
    state = [-1] * n
    dfs(0)
    print(max_honest)


def main():
    solve()


def __starting_point():
    main()
__starting_point()

import itertools

n = int(input())
tes = [[] for _ in range(n)]
for i in range(n):
    a = int(input())
    for _ in range(a):
        x, y = list(map(int, input().split()))
        tes[i].append([x - 1, y])
ans = 0 
for tf_s in itertools.product(list(range(2)), repeat = n):
    for i in range(n):
        if tf_s[i] == 0:
            continue
        for x, y in tes[i]:
            if tf_s[x] != y:
                break
        else:
            continue
        break
    else:
        ans = max(ans, tf_s.count(1))
print(ans)


# bit全探索
n = int(input())
# 各人における別の人への証言
q = [["-"] * n for _ in range(n)]
for i in range(n):
    a = int(input())
    for j in range(a):
        x, y = map(int, input().split())
        q[i][x - 1] = False if y == 0 else True
ans = 0
for bit in range(1 << n):
    arr = [False] * n
    for i in range(n):
        if bit >> i & 1 == 1:
            arr[i] = True
    flag = True
    for i in range(n):
        if arr[i] == False:
            # 不親切の人のいうことは聞く必要ない
            continue
        # 人iは正直者だと仮定して探索
        for j in range(n):
            if q[i][j] == "-":
                # そもそも言及してない
                continue
            if q[i][j] != arr[j]:
                # 仮定がくずれた
                flag = False
                break
    if flag:
        ans = max(ans, arr.count(True))
print(ans)

from itertools import product

n = int(input())

d = {}
for i in range(n):
  a = int(input())
  for _ in range(a):
    x, y = map(int, input().split())
    if i + 1 not in d:
      d[i + 1] = []
    d[i + 1].append((x, y))

ret = 0
for x in product((0, 1), repeat=n):
  ok = True
  for i in range(n):
    if x[i] == 0 or i + 1 not in d:
      continue
    for p, tf in d[i + 1]:
      if x[p - 1] != tf:
        ok = False
        break
    if not ok:
      break
  if ok:
    ret = max(ret, sum(x))

print(ret)

N=int(input())
xy = [[] for _ in range(N)]
for i in range(N):
    a = int(input())
    for _ in range(a):
        x,y = map(int,input().split())
        x -= 1
        xy[i].append((x,y))
ans = 0
s = set()
t = set()
def true(s,t,j):
    if j not in t:
        s.add(j)
        return False
    return True
def false(s,t,j):
    if j not in s:
        t.add(j)
        return False
    return True
def chk(i):
    s = set()
    t = set()
    fl = False
    for j in range(N):
        if (i>>j)&1:
            fl |= true(s,t,j)
            for x,y in xy[j]:
                fl |= true(s,t,x) if y == 1 else false(s,t,x)
        else:
            fl |= false(s,t,j)
    return fl
ans = 0
for i in range(2**N):
    if chk(i):
        continue
    cnt = 0
    for j in range(N):
        if (i>>j)&1:
            cnt += 1
    ans = max(ans, cnt)
print(ans)

import sys
input = sys.stdin.readline

#l = list(map(int, input().split()))
#import numpy as np
#arr = np.array([int(i) for i in input().split()])
'''
a,b=[],[]
for i in range(n):
    A, B = map(int, input().split())
    a.append(A)   
    b.append(B)'''


n=int(input())

a,x=[],[]
for i in range(n):
    A = int(input())
    a.append(A)
    B=[]
    for j in range(A):
        B.append(list(map(int, input().split())))
    x.append(B)

ma=0
for i in range(2**n):
    now=0
    flg=True
    e=[0]*n
    for j in range(n):
        if (i>>j)&1:
            now+=1
            e[j]=1

    for j in range(n):
        #print(e)
        if (i>>j)&1:
            
            if e[j]==0:
                flg=False
                break
            elif not flg:
                break

            for k in range(a[j]):
                """if e[x[j][k][0]-1]==-1: 
                    if x[j][k][1] and
                    e[x[j][k][0]-1]=x[j][k][1]"""
                
                if (e[x[j][k][0]-1]==0 and x[j][k][1]==1) or (e[x[j][k][0]-1]==1 and x[j][k][1]==0):
                    flg=False
                    break

    if flg and ma<now:
        ma=now
        #print(ma)

print(ma)