Problem:
Score : 800 points

Problem Statement

You are given a string S consisting of lowercase English letters.
Determine whether we can turn S into a palindrome by repeating the operation of swapping two adjacent characters. If it is possible, find the minimum required number of operations.

Constraints

1 \leq |S| \leq 2 × 10^5

S consists of lowercase English letters.

Input

Input is given from Standard Input in the following format:

S

Output

If we cannot turn S into a palindrome, print -1. Otherwise, print the minimum required number of operations.

Sample Input 1

eel

Sample Output 1

1

We can turn S into a palindrome by the following operation:

Swap the 2-nd and 3-rd characters. S is now ele.

Sample Input 2

ataatmma

Sample Output 2

4

We can turn S into a palindrome by the following operation:

Swap the 5-th and 6-th characters. S is now ataamtma.

Swap the 4-th and 5-th characters. S is now atamatma.

Swap the 3-rd and 4-th characters. S is now atmaatma.

Swap the 2-nd and 3-rd characters. S is now amtaatma.

Sample Input 3

snuke

Sample Output 3

-1

We cannot turn S into a palindrome.

Solution in Rust (1.15.1) (judge verdict: Accepted)

use std::io::*;
use std::str::FromStr;

#[allow(dead_code)]
fn read<T: FromStr>() -> T {
    let stdin = stdin();
    let stdin = stdin.lock();
    let token: String = stdin
        .bytes()
        .map(|c| c.expect("failed to read char") as char)
        .skip_while(|c| c.is_whitespace())
        .take_while(|c| !c.is_whitespace())
        .collect();
    token.parse().ok().expect("failed to parse token")
}

#[allow(dead_code)]
struct FenwickTree {
    seq: Vec<i64>,
}
#[allow(dead_code)]
impl FenwickTree {
    fn new(n: usize) -> FenwickTree {
        FenwickTree { seq: vec![0; n + 2] }
    }
    fn add(&mut self, index: usize, value: i64) {
        let mut index = (index + 1) as i32;
        while (index as usize) < self.seq.len() {
            self.seq[index as usize] += value;
            index += index & -index;
        }
    }
    // inclusive
    fn sum(&self, index: usize) -> i64 {
        let mut ret = 0;
        let mut index = (index + 1) as i32;
        while index > 0 {
            ret += self.seq[index as usize];
            index -= index & -index;
        }
        ret
    }
}

struct Solver {
    s: Vec<char>,
}

impl Solver {
    fn new() -> Solver {
        Solver { s: read::<String>().chars().collect::<Vec<char>>(), }
    }
    fn solve(&mut self) {
        let s: &Vec<char> = &self.s;
        let n = s.len();
        let mut indexs = vec![vec![]; 200];
        for i in 0..n {
            indexs[s[i] as usize].push(i);
        }
        let odd_cnt = indexs.iter().filter(|vs| vs.len() != 0 && vs.len() % 2 == 1).count();
        if odd_cnt > 1 {
            println!("-1");
            return;
        }
        let mut dests = vec![None; n];
        let mut srcs = vec![None; n];
        let mut ans = 0;
        let mut mid = None;
        for index in indexs.iter() {
            for i in 0..index.len() / 2 {
                let revi = index.len() - i - 1;
                dests[index[i]] = Some(index[revi]);
                srcs[index[revi]] = Some(index[i]);
            }
            if index.len() % 2 == 1 {
                mid = Some(index[index.len() / 2]);
            }
        }   
        let mut starts = FenwickTree::new(n);
        let mut ends = FenwickTree::new(n);
        for pos in 0..n {
            if let Some(src) = srcs[pos] {
                starts.add(src, -1);
                let inner = (ends.sum(pos) - ends.sum(src)) as usize;
                let mut intersect = (pos - src - 1) - inner * 2;
                if let Some(mid) = mid {
                    if mid < src || pos < mid {
                        ans += 2;
                    } else {
                        intersect -= 1;
                    }
                }
                let over = starts.sum(src) as usize;
                let outer = n / 2 - 1 - inner - intersect - over;
                ans += intersect + outer * 2;
                ends.add(src, 1);
            }
            if let Some(_) = dests[pos] {
                starts.add(pos, 1);
            }
        }
        println!("{}", ans / 2);
    }
}

fn main() {
    let mut solver = Solver::new();
    solver.solve();
}