Problem:
Score : 700 points

Problem Statement

We have a string s consisting of lowercase English letters.
Snuke is partitioning s into some number of non-empty substrings.
Let the subtrings obtained be s_1, s_2, ..., s_N from left to right. (Here, s = s_1 + s_2 + ... + s_N holds.)
Snuke wants to satisfy the following condition:

For each i (1 \leq i \leq N), it is possible to permute the characters in s_i and obtain a palindrome.

Find the minimum possible value of N when the partition satisfies the condition.

Constraints

1 \leq |s| \leq 2 \times 10^5

s consists of lowercase English letters.

Input

Input is given from Standard Input in the following format:

s

Output

Print the minimum possible value of N when the partition satisfies the condition.

Sample Input 1

aabxyyzz

Sample Output 1

2

The solution is to partition s as aabxyyzz = aab + xyyzz.
Here, aab can be permuted to form a palindrome aba, and xyyzz can be permuted to form a palindrome zyxyz.

Sample Input 2

byebye

Sample Output 2

1

byebye can be permuted to form a palindrome byeeyb.

Sample Input 3

abcdefghijklmnopqrstuvwxyz

Sample Output 3

26

Sample Input 4

abcabcxabcx

Sample Output 4

3

The solution is to partition s as abcabcxabcx = a + b + cabcxabcx.

Solution in C++14 (GCC 5.4.1) (judge verdict: Runtime Error)

#include<iostream>
#include<cstdio>
#include<vector>
#include<string>
#include<functional>
#include<queue>
#include<map>
#include<cmath>
#include<algorithm>
#include<bitset>
#include<utility>
#include<complex>
#include<cstdlib>
#include<set>
#include<cctype>

#define DBG cerr << '!' << endl;
#define REP(i,n) for(int (i) = (0);(i) < (n);++i)
#define rep(i,s,g) for(int (i) = (s);(i) < (g);++i)
#define rrep(i,s,g) for(int (i) = (s);i >= (g);--(i))
#define PB push_back
#define MP make_pair
#define FI first
#define SE second
#define SHOW1d(v,n) {for(int i = 0;i < (n);i++)cerr << v[i] << ' ';cerr << endl << endl;}
#define SHOW2d(v,i,j) {for(int a = 0;a < i;a++){for(int b = 0;b < j;b++)cerr << v[a][b] << ' ';cerr << endl;}cerr << endl;}
#define ALL(v) v.begin(),v.end()

using namespace std;

typedef long long ll;
typedef vector<int> iv;
typedef vector<iv> iiv;
typedef vector<string> sv;

bitset<27> dp[1000000];
map<pair<int,int>,int> mp;



int dfs(int left,int right)
{
	if(mp.find(MP(left,right)) != mp.end())
	{
		return mp[MP(left,right)];
	}
	if((dp[left]^dp[right]).count() == 0 || left == right)return 1;
	int mi = 100000000;
	int count = 0;
	int a = left,b = right;
	
	while(b - a >= 0)
	{
		bitset<27> tmp = dp[a]^dp[b];
		if(tmp.count() <= 1)
		{
			mi = min(mi,dfs(left,a)+dfs(b+1,right)+1);
		}
		if(count % 2 == 0)
		{
			a++;
		}
		else
		{
			b--;
		}
		count++;
	}
	a = left,b = right;
	
	while(b - a >= 0)
	{
		bitset<27> tmp = dp[a]^dp[b];
		if(tmp.count() <= 1)
		{
			mi = min(mi,dfs(left,a)+1);
		}
		{
			a++;
		}
	}
	a = left,b = right;
	
	while(b - a >= 0)
	{
		bitset<27> tmp = dp[a]^dp[b];
		if(tmp.count() <= 1)
		{
			mi = min(mi,dfs(b+1,right)+1);
		}
		{
			b--;
		}
	}

	//cout << '!' << endl;
	return mp[MP(left,right)] = mi;
	
	
}
	



int main()
{
	string str;
	cin >> str;
	
	dp[1][str[0]-'a'] = 1;
	
	
	
	for(int i = 1;i < str.size();i++)
	{
		bitset<27> tmp(1<<(str[i]-'a'));
		dp[i+1] = dp[i]^tmp;
	
	}
	/*
	REP(i,str.size()+1)
	{
		cout << dp[i] << endl;
	}
	*/
	cout << dfs(1,str.size()) << endl;
	
	return 0;
}