Problem:
Score : 1000 points

Problem Statement

You have two strings A = A_1 A_2 ... A_n and B = B_1 B_2 ... B_n of the same length consisting of 0 and 1.

You can transform A using the following operations in any order and as many times as you want:

Shift A by one character to the left (i.e., if A = A_1 A_2 ... A_n, replace A with A_2 A_3 ... A_n A_1).

Shift A by one character to the right (i.e., if A = A_1 A_2 ... A_n, replace A with A_n A_1 A_2 ... A_{n-1}).

Choose any i such that B_i = 1. Flip A_i (i.e., set A_i = 1 - A_i).

You goal is to make strings A and B equal.

Print the smallest number of operations required to achieve this, or -1 if the goal is unreachable.

Constraints

1 \leq |A| = |B| \leq 2,000

A and B consist of 0 and 1.

Input

Input is given from Standard Input in the following format:

A
B

Output

Print the smallest number of operations required to make strings A and B equal, or -1 if the goal is unreachable.

Sample Input 1

1010
1100

Sample Output 1

3

Here is one fastest way to achieve the goal:

Flip A_1: A = 0010

Shift A to the left: A = 0100

Flip A_1 again: A = 1100

Sample Input 2

1
0

Sample Output 2

-1

There is no way to flip the only bit in A.

Sample Input 3

11010
10001

Sample Output 3

4

Here is one fastest way to achieve the goal:

Shift A to the right: A = 01101

Flip A_5: A = 01100

Shift A to the left: A = 11000

Shift A to the left again: A = 10001

Sample Input 4

0100100
1111111

Sample Output 4

5

Flip A_1, A_3, A_4, A_6 and A_7 in any order.

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

#include<set>
#include<map>
#include<deque>
#include<queue>
#include<stack>
#include<cmath>
#include<ctime>
#include<bitset>
#include<string>
#include<vector>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<climits>
#include<complex>
#include<iostream>
#include<algorithm>
#define ll long long
#define inf 1e9
using namespace std;
 
inline void up(int &x,const int &y){if(x<y)x=y;}
inline void down(int &x,const int &y){if(x>y)x=y;}
const int maxn = 11000;
 
int n;
char s1[maxn],s2[maxn];
int pre1[maxn],pre2[maxn],topre[maxn],nex[maxn];
 
int cal(const int x,const int y)
{
	if(x<y) return pre2[x]+pre2[n]-pre2[y-1];
	else return pre2[x]-pre2[y-1];
}
int find_pre(const int x)
{
	if(topre[x]) return x-topre[x];
	else return x+n-topre[n];
}
int find_nex(const int x)
{
	if(nex[x]!=n+1) return nex[x]-x;
	else return nex[1]+n-x;
}
struct node{int left,right;}t[maxn]; int tp,mx[maxn];
inline bool cmp(const node x,const node y){return x.left<y.left;}
int solve()
{
	int re=inf;
	for(int i=0;i<n;i++)
	{
		int now=0; tp=0;
		for(int j=1;j<=n;j++)
		{
			int r=j-i<=0?j-i+n:j-i;
			if(s1[j]!=s2[r]) 
			{
				now++;
				if(s1[j]=='0') continue;
				if(cal(j,r)==0)	t[++tp]=(node){find_pre(r),find_nex(j)};
			}
		}
		sort(t+1,t+tp+1,cmp);
		int cost; mx[tp+1]=0;
		for(int j=tp;j>=1;j--) mx[j]=max(mx[j+1],t[j].right);
		cost=mx[1]*2;
		for(int j=1;j<=tp;j++)
		{
			int k=j+1;for(;k<=tp&&t[k].left==t[j].left;k++);k--;
			down(cost,2*(t[j].left+mx[k+1]));
			j=k;
		}
		if(!tp) cost=0;
		down(re,now+cost+i);
	}
	return re;
}
 
int main()
{
	scanf("%s",s1+1); scanf("%s",s2+1); n=strlen(s1+1);
	for(int i=1;i<=n;i++)
		pre1[i]=pre1[i-1]+(s1[i]-'0'),
		pre2[i]=pre2[i-1]+(s2[i]-'0');
	for(int las=0,i=1;i<=n;i++)
	{
		if(s2[i]=='1') las=i;
		topre[i]=las;
	}
	for(int las=n+1,i=n;i>=1;i--)
	{
		if(s2[i]=='1') las=i;
		nex[i]=las;
	}
	if(pre1[n]&&!pre2[n]) {puts("-1");return 0;}
	
	int ans=solve();
	
	for(int i=1;i*2<=n;i++)
		swap(s1[i],s1[n-i+1]),
		swap(s2[i],s2[n-i+1]);
	for(int i=1;i<=n;i++)
		pre1[i]=pre1[i-1]+(s1[i]-'0'),
		pre2[i]=pre2[i-1]+(s2[i]-'0');
	for(int las=0,i=1;i<=n;i++)
	{
		if(s2[i]=='1') las=i;
		topre[i]=las;
	}
	for(int las=n+1,i=n;i>=1;i--)
	{
		if(s2[i]=='1') las=i;
		nex[i]=las;
	}
	down(ans,solve());
	
	printf("%d\n",ans);
	
	return 0;
}