#pragma GCC optimize("Ofast")
#pragma GCC optimize("unroll-loops")
#pragma GCC optimize("inline")
#include<bits/stdc++.h>
using namespace std;
template < class T> struct cLtraits_identity{
using type = T;
}
;
template < class T> using cLtraits_try_make_signed =
typename conditional<
is_integral< T> :: value ,
make_signed< T> ,
cLtraits_identity< T>
> :: type ;
template < class S, class T> struct cLtraits_common_type{
using tS = typename cLtraits_try_make_signed< S> :: type ;
using tT = typename cLtraits_try_make_signed< T> :: type ;
using type = typename common_type< tS,tT> :: type ;
}
;
template < class S, class T> inline auto min_L( S a, T b)
- > typename cLtraits_common_type< S,T> :: type {
return ( typename cLtraits_common_type< S,T> :: type ) a <= ( typename cLtraits_common_type< S,T> :: type ) b ? a : b;
}
#define main dummy_main
int main( ) {
return 0 ;
}
#undef main
class Solution{
public :
int longestPalindrome( vector< string> & words) {
int i;
int j;
int res = 0 ;
int cnt[ 26 ] [ 26 ] = { } ;
for ( string s : words) {
cnt[ s[ 0 ] - 'a' ] [ s[ 1 ] - 'a' ] ++ ;
}
for ( i= ( 0 ) ; i< ( 26 ) ; i++ ) {
for ( j= ( i+ 1 ) ; j< ( 26 ) ; j++ ) {
res + = 4 * min_L( cnt[ i] [ j] , cnt[ j] [ i] ) ;
}
}
for ( i= ( 0 ) ; i< ( 26 ) ; i++ ) {
res + = 4 * ( cnt[ i] [ i] / 2 ) ;
cnt[ i] [ i] % = 2 ;
}
for ( i= ( 0 ) ; i< ( 26 ) ; i++ ) {
if ( cnt[ i] [ i] ) {
res+ = 2 ;
break ;
}
}
return res;
}
}
;
// cLay version 20220312-1
// --- original code ---
// #define main dummy_main
// {}
// #undef main
//
// class Solution {
// public:
// int longestPalindrome(vector<string>& words) {
// int i, j, res = 0;
// int cnt[26][26] = {};
// for(string s : words) cnt[s[0]-'a'][s[1]-'a']++;
// rep(i,26) rep(j,i+1,26) res += 4 * min(cnt[i][j], cnt[j][i]);
// rep(i,26){
// res += 4 * (cnt[i][i] / 2);
// cnt[i][i] %= 2;
// }
// rep(i,26) if(cnt[i][i]) res+=2, break;
// return res;
// }
// };
I3ByYWdtYSBHQ0Mgb3B0aW1pemUoIk9mYXN0IikKI3ByYWdtYSBHQ0Mgb3B0aW1pemUoInVucm9sbC1sb29wcyIpCiNwcmFnbWEgR0NDIG9wdGltaXplKCJpbmxpbmUiKQojaW5jbHVkZTxiaXRzL3N0ZGMrKy5oPgp1c2luZyBuYW1lc3BhY2Ugc3RkOwp0ZW1wbGF0ZTxjbGFzcyBUPiBzdHJ1Y3QgY0x0cmFpdHNfaWRlbnRpdHl7CiAgdXNpbmcgdHlwZSA9IFQ7Cn0KOwp0ZW1wbGF0ZTxjbGFzcyBUPiB1c2luZyBjTHRyYWl0c190cnlfbWFrZV9zaWduZWQgPQogIHR5cGVuYW1lIGNvbmRpdGlvbmFsPAogICAgaXNfaW50ZWdyYWw8VD46OnZhbHVlLAogICAgbWFrZV9zaWduZWQ8VD4sCiAgICBjTHRyYWl0c19pZGVudGl0eTxUPgogICAgPjo6dHlwZTsKdGVtcGxhdGUgPGNsYXNzIFMsIGNsYXNzIFQ+IHN0cnVjdCBjTHRyYWl0c19jb21tb25fdHlwZXsKICB1c2luZyB0UyA9IHR5cGVuYW1lIGNMdHJhaXRzX3RyeV9tYWtlX3NpZ25lZDxTPjo6dHlwZTsKICB1c2luZyB0VCA9IHR5cGVuYW1lIGNMdHJhaXRzX3RyeV9tYWtlX3NpZ25lZDxUPjo6dHlwZTsKICB1c2luZyB0eXBlID0gdHlwZW5hbWUgY29tbW9uX3R5cGU8dFMsdFQ+Ojp0eXBlOwp9CjsKdGVtcGxhdGU8Y2xhc3MgUywgY2xhc3MgVD4gaW5saW5lIGF1dG8gbWluX0woUyBhLCBUIGIpCi0+IHR5cGVuYW1lIGNMdHJhaXRzX2NvbW1vbl90eXBlPFMsVD46OnR5cGV7CiAgcmV0dXJuICh0eXBlbmFtZSBjTHRyYWl0c19jb21tb25fdHlwZTxTLFQ+Ojp0eXBlKSBhIDw9ICh0eXBlbmFtZSBjTHRyYWl0c19jb21tb25fdHlwZTxTLFQ+Ojp0eXBlKSBiID8gYSA6IGI7Cn0KI2RlZmluZSBtYWluIGR1bW15X21haW4KaW50IG1haW4oKXsKICByZXR1cm4gMDsKfQojdW5kZWYgbWFpbgpjbGFzcyBTb2x1dGlvbnsKICBwdWJsaWM6CiAgaW50IGxvbmdlc3RQYWxpbmRyb21lKHZlY3RvcjxzdHJpbmc+JiB3b3Jkcyl7CiAgICBpbnQgaTsKICAgIGludCBqOwogICAgaW50IHJlcyA9IDA7CiAgICBpbnQgY250WzI2XVsyNl0gPSB7fTsKICAgIGZvcihzdHJpbmcgcyA6IHdvcmRzKXsKICAgICAgY250W3NbMF0tJ2EnXVtzWzFdLSdhJ10rKzsKICAgIH0KICAgIGZvcihpPSgwKTtpPCgyNik7aSsrKXsKICAgICAgZm9yKGo9KGkrMSk7ajwoMjYpO2orKyl7CiAgICAgICAgcmVzICs9IDQgKm1pbl9MKGNudFtpXVtqXSwgY250W2pdW2ldKTsKICAgICAgfQogICAgfQogICAgZm9yKGk9KDApO2k8KDI2KTtpKyspewogICAgICByZXMgKz0gNCAqIChjbnRbaV1baV0gLyAyKTsKICAgICAgY250W2ldW2ldICU9IDI7CiAgICB9CiAgICBmb3IoaT0oMCk7aTwoMjYpO2krKyl7CiAgICAgIGlmKGNudFtpXVtpXSl7CiAgICAgICAgcmVzKz0yOwogICAgICAgIGJyZWFrOwogICAgICB9CiAgICB9CiAgICByZXR1cm4gcmVzOwogIH0KfQo7Ci8vIGNMYXkgdmVyc2lvbiAyMDIyMDMxMi0xCgovLyAtLS0gb3JpZ2luYWwgY29kZSAtLS0KLy8gI2RlZmluZSBtYWluIGR1bW15X21haW4KLy8ge30KLy8gI3VuZGVmIG1haW4KLy8gCi8vIGNsYXNzIFNvbHV0aW9uIHsKLy8gcHVibGljOgovLyAgIGludCBsb25nZXN0UGFsaW5kcm9tZSh2ZWN0b3I8c3RyaW5nPiYgd29yZHMpIHsKLy8gICAgIGludCBpLCBqLCByZXMgPSAwOwovLyAgICAgaW50IGNudFsyNl1bMjZdID0ge307Ci8vICAgICBmb3Ioc3RyaW5nIHMgOiB3b3JkcykgY250W3NbMF0tJ2EnXVtzWzFdLSdhJ10rKzsKLy8gICAgIHJlcChpLDI2KSByZXAoaixpKzEsMjYpIHJlcyArPSA0ICogbWluKGNudFtpXVtqXSwgY250W2pdW2ldKTsKLy8gICAgIHJlcChpLDI2KXsKLy8gICAgICAgcmVzICs9IDQgKiAoY250W2ldW2ldIC8gMik7Ci8vICAgICAgIGNudFtpXVtpXSAlPSAyOwovLyAgICAgfQovLyAgICAgcmVwKGksMjYpIGlmKGNudFtpXVtpXSkgcmVzKz0yLCBicmVhazsKLy8gICAgIHJldHVybiByZXM7Ci8vICAgfQovLyB9Owo=