#include <bits/stdc++.h>
#pragma comment(linker, "/STACK:102400000,102400000")
using namespace std;
const int maxn = 210;
const long long INF = 0x3f3f3f3f3f3f3f3f;
struct Matrix {
  long long n[maxn][maxn], siz;
  Matrix(int _siz = maxn) {
    memset(n, -1, sizeof(n));
    siz = _siz;
  }
  void E() {
    memset(n, -1, sizeof(n));
    for (int i = 0; i < siz; i++) n[i][i] = 0;
  }
  Matrix operator*(const Matrix &v) const {
    Matrix tem(siz);
    for (int i = 0; i < siz; i++)
      for (int j = 0; j < siz; j++)
        for (int k = 0; k < siz; k++)
          if (~n[i][k] && ~v.n[k][j])
            tem.n[i][j] = max(tem.n[i][j], n[i][k] + v.n[k][j]);
    return tem;
  }
  void pri() {
    for (int i = 0; i < siz; i++) {
      for (int j = 0; j < siz; j++) printf("%3lld", n[i][j]);
      puts("");
    }
  }
};
Matrix Pow(Matrix x, long long n) {
  Matrix res;
  res.E();
  while (n) {
    if (n & 1) res = x * res;
    x = x * x;
    n >>= 1;
  }
  return res;
}
struct AC_Auto {
  const static int nsiz = 26;
  struct node {
    char chr;
    int fail, nxt[nsiz];
    long long val;
  } trie[maxn];
  int siz;
  int chnum(char a) { return a - 'a'; }
  void init() {
    siz = 0;
    memset(trie, 0, sizeof(trie));
  }
  void addstr(char *, int);
  void construct();
  long long solve(long long);
};
int N;
long long L;
int A[maxn];
char patn[maxn];
AC_Auto ac;
Matrix ans, res;
int main() {
  ac.init();
  scanf("%d%lld", &N, &L);
  for (int i = 0; i < N; i++) scanf("%d", &A[i]);
  for (int i = 0; i < N; i++) {
    scanf(" %s", patn);
    ac.addstr(patn, A[i]);
  }
  ac.construct();
  printf("%lld\n", ac.solve(L));
  return 0;
}
long long AC_Auto::solve(long long len) {
  Matrix res(siz + 1);
  for (int np = 0; np <= siz; np++) {
    for (int i = 0; i < nsiz; i++) {
      int nxp = trie[np].nxt[i];
      if (nxp) res.n[nxp][np] = max(res.n[nxp][np], (long long)trie[nxp].val);
    }
  }
  res = Pow(res, len);
  long long ans = 0;
  for (int i = 1; i <= siz; i++) ans = max(ans, res.n[i][0]);
  return ans;
}
void AC_Auto::addstr(char str[], int val) {
  int np = 0, len = strlen(str);
  for (int i = 0; i < len; i++) {
    int chn = chnum(str[i]);
    if (trie[np].nxt[chn])
      np = trie[np].nxt[chn];
    else {
      trie[np].nxt[chn] = ++siz;
      np = siz;
      trie[np].chr = str[i];
    }
    if (i == len - 1) trie[np].val += val;
  }
}
void AC_Auto::construct() {
  queue<int> que;
  for (int i = 0; i < nsiz; i++) {
    int np = trie[0].nxt[i];
    if (np) que.push(np);
  }
  while (que.size()) {
    int np = que.front();
    que.pop();
    for (int i = 0; i < nsiz; i++) {
      int nxp = trie[np].nxt[i];
      int fap = trie[np].fail;
      if (!nxp)
        trie[np].nxt[i] = trie[fap].nxt[i];
      else {
        que.push(nxp);
        trie[nxp].fail = trie[fap].nxt[i];
        fap = trie[nxp].fail;
        trie[nxp].val += trie[fap].val;
      }
    }
  }
}
