#include <iostream>
#include <iomanip>
#include <vector>
#include <algorithm>
#include <numeric>
#include <functional>
#include <cmath>
#include <queue>
#include <stack>
#include <string>
#include <chrono>
#include<map>

#define repd(i,a,b) for (int i=(a);i<(b);i++)
#define rep(i,n) repd(i,0,n)
typedef long long ll;
typedef unsigned int ui;
typedef unsigned short us;
typedef unsigned long long ull;

using namespace std;


int inputValue() {
  int a;
  scanf("%d", &a);
  return a;
};
void inputVector(vector<int>* v) {
  int a;
  while (cin >> a) {
    if (a == -1)break;
    v->push_back(a);
  }
};

void inputVector(vector<int> * p, int a) {
  p->clear();
  p->shrink_to_fit();
  rep(i, a) {
    int input;
    cin >> input;
    p->push_back(input);
  }
}

void inputVector2(vector<vector<int>>& v, ui r, ui c) {
  int temp;
  for (size_t i = 0; i < r; i++)
  {
    for (size_t j = 0; j < c; j++)
    {
      scanf("%d", &temp);
      v[i][j] = temp;
    }
  }
}
void inputVector3(vector<int>* v0, vector<int>* v1) {
  int a;
  unsigned short count = 0b0;
  while (cin >> a) {
    if (a == -1)break;
    if (count)v0->push_back(a); else v1->push_back(a);
    count = count ^ 1;
  }
};

template <typename T>
void output(T a, int precision) {
  if (precision > 0) {
    cout << setprecision(precision) << a << "\n";
  }
  else {
    cout << a << "\n";
  }
}

template<template <class...> class Map, typename T_0, typename T_1, typename... Args>
void inputMap(Map<T_0, T_1, Args...>& mp) {
  T_0 a;
  T_1 b;
  while (cin >> a && a != -1) {
    cin >> b;
    mp.insert(make_pair(a, b));
  }
}
template<template <class...> class Vec1, template <class...> class Vec2, typename T, typename... Args1, typename... Args2>
void input2dPairVector(Vec1<Vec2<T, Args2...>, Args1...>& vec) {
  T a;
  T b;
  while (cin >> a && a != -1) {
    cin >> b;
    vec.push_back(vector<T>({ a - 1, b - 1 }));
  }
}
template<template <class...> class Vec1, template <class...> class Vec2, typename T, typename... Args1, typename... Args2>
void input2dPairVector(Vec1<Vec2<T, Args2...>, Args1...>& vec, ull size) {
  T a;
  T b;
  for (size_t i = 0; i < size; i++) {
    scanf("%d %d", &a, &b);
    vec.push_back(vector<T>({ a - 1, b - 1 }));
  }
}

template<template <class...> class Vec, typename T, typename U, typename... Args>
void numberToBoolenVector(Vec<T, Args...>& vec, U a) {
  ui i = 0;
  T amari;
  do {
    if (a % (ull)pow(2, i + 1)) {
      amari = 1;
      vec.push_back(amari);
      a -= (ull)pow(2, i);
    }
    else {
      amari = 0;
      vec.push_back(amari);
    }
    i++;
  } while (a);
}

template<template <class...> class Vec, typename T, typename... Args>
ull boolenVectorToNumber(Vec<T, Args...>& vec) {
  ull r = 0;
  for (size_t i = 0; i < vec.size(); i++)
  {
    r += vec[i] * (ull)pow(2, i);
  }
  return r;
}

ui bitCount(ui i) {
  i = i - ((i >> 1) & 0x55555555);
  i = (i & 0x33333333) + ((i >> 2) & 0x33333333);
  i = (i + (i >> 4)) & 0x0f0f0f0f;
  i = i + (i >> 8);
  i = i + (i >> 16);
  return i & 0x3f;
}

int main(int argc, const char * argv[]) {
  int n, m;
  scanf("%d %d", &n, &m);
  auto vec = vector<ull>((ui)pow(2, n));
  iota(vec.begin(), vec.end(), 0);

  auto kazoe = vector<ui>();
  for (size_t i = 0; i < m; i++)
  {
    int k;
    scanf("%d", &k);
    ui kazoe_tmp = 0;
    for (size_t j = 0; j < k; j++) {
      int tmp01;
      scanf("%d", &tmp01);
      kazoe_tmp += (ui)pow(2, tmp01-1);
    }
    kazoe.push_back(kazoe_tmp);
  }
  
  for (size_t i = 0; i < m; i++)
  {
    int guki;
    scanf("%d", &guki);
    for (int j = vec.size() - 1; j >= 0; j--)
    {
      int kazu = bitCount(vec[j] & kazoe[i]) % 2;
      if (kazu != guki)
      {
        vec.erase(vec.begin()+j);
      }
    }
  }

  printf("%d", vec.size());
}


Measured memory_bytes: 512