#include<bits/stdc++.h>
using namespace std;
#define INF 0x3f3f3f3f3f3f
const int N=1<<16;
#define ll long long
int a[20],dp[N],v[N];
int dfs(int st,int now)
{
    if(~dp[st])return dp[st];
    int ans=0;
    for(int s=st; s; s=(s-1)&st)
        if(v[s])ans=max(dfs(st-s,now+v[s])+a[now+v[s]],ans);
    return dp[st]=ans;
}
int main()
{
    int n,m,s=0;
    cin>>n>>m;
    for(int i=0; i<n; i++)
        cin>>a[i],s+=a[i];
    sort(a,a+n,greater<int>());
    for(int i=0; i<m; i++)
    {
        int x,y;
        cin>>x;
        int st=0;
        for(int j=0; j<x; j++)
        {
            cin>>y;
            y--;
            st|=(1<<y);
        }
        v[st]=x;
    }
    memset(dp,-1,sizeof dp);
    s-=dfs((1<<n)-1,-1);
    cout<<s<<endl;
}

一开始想通过m个状态来组合出最优的,想到m^2都不能跑就觉得好难。后来经过提示复杂度O(3^n)后,才想到枚举子集的子集。反过来确定是否有m。太爽了,自己想到的感觉是不一样