Problem:
MathJax.Hub.Config({
tex2jax: {inlineMath: [['$','$'], ['\\(','\\)']]}
});

E: 28

問題文

トランプゲームの大富豪において，ランクが $2$, $8$ のカードは強力です．
そこで，$10$ 進数表記で数字の $2$, $8$ のみからなる整数を良い整数と呼ぶことにします．
良い整数を小さいものから列挙すると $2, 8, 22, 28, 82, 88, \cdots$ となります．

$n$ を正の整数とします．$n$ が良い整数の積の形で表現できるとき，
最大でいくつの積になるか求めてください．できないなら $-1$ と出力してください．

入力

$n$

制約

$1 \leq n \leq 10^{18}$

出力

答えを $1$ 行で出力してください．

サンプル

サンプル入力1

1

サンプル出力1

-1

サンプル入力2

2

サンプル出力2

1

サンプル入力3

88

サンプル出力3

3

$2 \times 2 \times 22$ と表せます．

サンプル入力4

100

サンプル出力4

-1

サンプル入力5

173553147234869248

サンプル出力5

11

$2^6 \times 28 \times 2222^3 \times 8828$ と表せます．

Solution in C++11 (judge verdict: Time Limit Exceeded)

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
vector<ll> nex[20];
vector<ll> nv;

unordered_map<ll,int> memo;
set<ll> ok;

const int INF = (1<<29);
ll solve(ll x){
  bool f = false;
  if( memo.count(x) != 0 ) return memo[x];
  int ret = INF;
  for(int i=nv.size()-1;i>-1;i--){ 
    if( x == nv[i] ){
      f = true; continue;
    }
    if( x % nv[i] == 0 ){
      //  cout << x/nv[i] << " - "<<  nv[i] << endl;
      int l = solve(x/nv[i]);
      int r = solve(nv[i]);
      if( l == -1 || r== -1 ) continue;
      ret = min( l+r, ret );
    }
  }
  if( ret == INF ){
    if( !f ) return memo[x] = -1;
    return memo[x] = 1;
  }
  return memo[x] = ret;
}


bool check( ll x ,const vector<ll>& v){
  for(int i=0;i<(int)v.size();i++){
    if( v[i] == x ) continue;
    if( x % v[i] == 0 ) return true;
  }
  return false;
}

int main(){
  nex[0].push_back( 2 );
  nex[0].push_back( 8 );
  for(int k=0;k<18;k++){
    for(int i=0;i<(int)nex[k].size();i++){
      ll p = nex[k][i];
      nex[k+1].push_back( p*10 + 2LL );
      nex[k+1].push_back( p*10 + 8LL ); 
    }
  }
  for(int k=0;k<18;k++){
    for(int i=0;i<nex[k].size();i++){
      nv.push_back( nex[k][i] );
      ok.insert(nex[k][i]);
    }
  }
  sort(nv.begin(),nv.end());
  ll n;
  cin >> n;
  cout << solve(n) << endl;
  
}