#include <bits/stdc++.h>
using namespace std;
int n, m;
char a[22][22];
int cost[22][22];
pair<int, int> moves[26][22];
int main() {
  gets(a[0]);
  sscanf(a[0], "%d%d", &n, &m);
  for (int i(0), _B_i(n); i < _B_i; ++i) gets(a[i]);
  vector<pair<int, int> > moves;
  for (int i(0), _B_i(n); i < _B_i; ++i) {
    int s = -1u / 2;
    for (int j(0), _B_j(m); j < _B_j; ++j) {
      scanf("%d", &cost[i][j]);
      s = min(s, cost[i][j]);
    }
    moves.push_back({1 << i, s});
  }
  for (int j(0), _B_j(m); j < _B_j; ++j) {
    vector<pair<int, int> > t(26);
    for (int i(0), _B_i(n); i < _B_i; ++i) {
      int c = a[i][j] - 'a';
      t[c].first |= 1 << i;
      t[c].second = min(t[c].second, -cost[i][j]);
    }
    for (int i(0), _B_i(n); i < _B_i; ++i)
      t[a[i][j] - 'a'].second += cost[i][j];
    for (int i(0), _B_i(26); i < _B_i; ++i)
      if (t[i].first) moves.push_back(t[i]);
  }
  vector<int> f(1 << n, -1u / 4);
  f[0] = 0;
  for (auto move : moves)
    for (int p = (1 << n); p-- > 0;)
      f[p | move.first] = min(f[p | move.first], f[p] + move.second);
  printf("%d\n", f.back());
  return 0;
}
