Problem:
Score : 900 points

Problem Statement

Takahashi has decided to give a string to his mother.

The value of a string T is the length of the longest common subsequence of T and T', where T' is the string obtained by reversing T.
That is, the value is the longest length of the following two strings that are equal: a subsequence of T (possibly non-contiguous), and a subsequence of T' (possibly non-contiguous).

Takahashi has a string S. He wants to give her mother a string of the highest possible value, so he would like to change at most K characters in S to any other characters in order to obtain a string of the highest possible value.
Find the highest possible value achievable.

Constraints

1 \leq |S| \leq 300

0 \leq K \leq |S|

S consists of lowercase English letters.

K is an integer.

Input

Input is given from Standard Input in the following format:

S
K

Output

Print the highest possible value achievable.

Sample Input 1

abcabcabc
1

Sample Output 1

7

Changing the first character to c results in cbcabcabc.
Let this tring be T, then one longest common subsequence of T and T' is cbabcbc, whose length is 7.

Sample Input 2

atcodergrandcontest
3

Sample Output 2

15

Solution in C# (Mono 4.6.2.0) (judge verdict: Wrong Answer)

using System;
using System.Collections.Generic;
using System.Collections;
using System.Collections.Specialized;
using System.Linq;
using System.Text;
using System.IO;
using System.Reflection;
using static System.Math;
using System.Numerics;
static class Program{
	const int mod=(int)1e9+7;
	static void Main(){
		Sc sc=new Sc();
		var s="$"+sc.S+"$";
		int n=sc.I;
		int ans=0;
		for(int i = 1;i<s.Length-1;i++) {
			ans=Max(ans,lcs2(s,i,i,n)-1);
			if(i<s.Length-2&&s[i]==s[i+1]){
				ans=Max(ans,lcs2(s,i,i+1,n));
			}
		}
		Console.WriteLine("{0}",ans);
	}
	static int lcs2(string s,int a,int b,int n){
		int[][] dp=new int[a+1][];
		int[][] dp2=new int[a+1][];
		int[][] dp3=new int[a+1][];
		int[][] dp4=new int[a+1][];
		dp[a]=new int[s.Length-b];
		dp2[a]=new int[s.Length-b];
		dp3[a]=new int[s.Length-b];
		dp4[a]=new int[s.Length-b];
		for(int i=a-1;i>=0;i--){
			dp[i]=new int[s.Length-b];
			dp2[i]=new int[s.Length-b];
			dp3[i]=new int[s.Length-b];
			dp4[i]=new int[s.Length-b];
			for(int j=1;j<dp[i].Length;j++){
				dp[i][j]=Max(dp[i+1][j],dp[i][j-1]);
				dp4[i][j]=Max(dp4[i+1][j],dp4[i][j-1]);
				if(s[i]==s[j+b]){
					dp[i][j]=Max(dp[i+1][j-1]+1,dp[i][j]);
					dp2[i][j]=0;
					dp3[i][j]=0;
					dp4[i][j]+=Min(dp2[i][j-1],dp3[i+1][j]);
				}
				else{
					if(dp[i][j]!=dp[i][j-1]){dp2[i][j]=0;}
					else{dp2[i][j]=dp2[i][j-1]+1;}
					if(dp[i][j]!=dp[i+1][j]){dp3[i][j]=0;}
					else{dp3[i][j]=dp3[i+1][j]+1;}
				}
			}
		}
		return dp[0][s.Length-b-1]*2+Min(dp4[0][s.Length-b-1],n)*2;
	}
}

public class Sc{
	public int I{get{return int.Parse(Console.ReadLine());}}
	public long L{get{return long.Parse(Console.ReadLine());}}
	public double D{get{return double.Parse(Console.ReadLine());}}
	public string S{get{return Console.ReadLine();}}
	public int[] Ia{get{return Array.ConvertAll(Console.ReadLine().Split(),int.Parse);}}
	public long[] La{get{return Array.ConvertAll(Console.ReadLine().Split(),long.Parse);}}
	public double[] Da{get{return Array.ConvertAll(Console.ReadLine().Split(),double.Parse);}}
	public string[] Sa{get{return Console.ReadLine().Split();}}
	public object[] Oa{get{return Console.ReadLine().Split();}}
	public int[] Ia2{get{return Array.ConvertAll(("0 "+Console.ReadLine()+" 0").Split(),int.Parse);}}
	public int[] Ia3(int a){return Array.ConvertAll((a.ToString()+" "+Console.ReadLine()).Split(),int.Parse);}
	public int[] Ia3(bool a,int b,bool c,int d){return Array.ConvertAll(((a?b.ToString()+" ":"")+Console.ReadLine()+(c?" "+d.ToString():"")).Split(),int.Parse);}
	public long[] La2{get{return Array.ConvertAll(("0 "+Console.ReadLine()+" 0").Split(),long.Parse);}}
	public long[] La3(int a){return Array.ConvertAll((a.ToString()+" "+Console.ReadLine()).Split(),long.Parse);}
	public long[] La3(bool a,int b,bool c,int d){return Array.ConvertAll(((a?b.ToString()+" ":"")+Console.ReadLine()+(c?" "+d.ToString():"")).Split(),long.Parse);}
	public T[] Arr<T>(int n,Func<T> f){var a=new T[n];for(int i=0;i<n;i++){a[i]=f();}return a;}
	public T[] Arr<T>(int n,Func<int,T> f){var a=new T[n];for(int i=0;i<n;i++){a[i]=f(i);}return a;}
	public T[] Arr<T>(int n,Func<string[],T> f){var a=new T[n];for(int i=0;i<n;i++){a[i]=f(Console.ReadLine().Split());}return a;}
	public T[] Arr<T>(int n,Func<int,string[],T> f){var a=new T[n];for(int i=0;i<n;i++){a[i]=f(i,Console.ReadLine().Split());}return a;}
}