module Main where

import           Control.Monad
import           Debug.Trace
import qualified Data.Vector                   as V
import qualified Data.Vector.Mutable           as VM
import qualified Data.Vector.Unboxed           as VU
import qualified Data.Vector.Unboxed.Mutable   as VUM
import           Data.List
import qualified Data.ByteString               as BS
import qualified Data.ByteString.Char8         as BSC8
import           Data.Char
import           Data.Maybe
import           Data.Ord
import           Data.Vector.Algorithms.Search
import qualified Data.Array                    as A
import qualified Data.Array.Unboxed            as AU
import qualified Data.Array.IO                 as AIO



getvuil :: IO (VU.Vector Int)
getvuil = VU.unfoldr (BSC8.readInt . BSC8.dropWhile isSpace) <$> BSC8.getLine
readi :: BSC8.ByteString -> Int
readi = fst . fromJust . BSC8.readInt
readil :: BSC8.ByteString -> [Int]
readil = map readi . BSC8.words
geti :: IO Int
geti = readi <$> BSC8.getLine
getil :: IO [Int]
getil = readil <$> BSC8.getLine

getNis :: Int -> IO [(Int, BSC8.ByteString)]
getNis 0 = return []
getisl n = do
    [aFst, aSnd] <- BSC8.words <$> BSC8.getLine
    next         <- (getisl (n - 1))
    return ((readi aFst, aSnd) : next)

il2ss :: [Int] -> String
il2ss = unwords . map show

il2sn :: [Int] -> String
il2sn = unlines . map show

main :: IO ()
main = do
    aN <- geti
    aS <- VU.fromList <$> getLine
    let (rL, gL, bL) = searchS aS
    let rLV          = VU.fromList rL
    let gLV          = VU.fromList gL
    let bLV          = VU.fromList bL
    let combiLV = (VU.length rLV) * (VU.length gLV) * (VU.length bLV)
    let sSize        = VU.length aS
    let
        ret = if (length rL == 0) || (length gL == 0) || (length bL == 0)
            then 0
            else
                combiLV
                    - (VU.foldl
                          (\acc1 x ->
                              acc1
                                  + (VU.foldl
                                        (\acc2 y ->
                                            let
                                                rP = rLV VU.! x
                                                gP = gLV VU.! y
                                                pt1 =
                                                    if mod
                                                            ((rP + 1) + (gP + 1)
                                                            )
                                                            2
                                                        == 0
                                                    then
                                                        div
                                                            ((rP + 1) + (gP + 1)
                                                            )
                                                            2
                                                    else
                                                        -1
                                                pt2 = 2 * (rP + 1) - (gP + 1)
                                                pt3 = 2 * (gP + 1) - (rP + 1)
                                                pt  = nub $ filter
                                                    (\x ->
                                                        (x >= 1) && (x <= sSize)
                                                    )
                                                    [pt1, pt2, pt3]
                                            in
                                                acc2
                                                    + foldl
                                                          (\acc x ->
                                                              if aS
                                                                  VU.! (x - 1)
                                                                  ==   'B'
                                                              then
                                                                  acc + 1
                                                              else
                                                                  acc
                                                          )
                                                          0
                                                          pt
                                        )
                                        0
                                        (VU.fromList [0 .. VU.length gLV - 1])
                                    )
                          )
                          0
                          (VU.fromList [0 .. VU.length rLV - 1])
                      )

    print ret


searchS :: VU.Vector Char -> ([Int], [Int], [Int])
searchS vec = searchS' vec (VU.length vec - 1) ([], [], [])

searchS'
    :: VU.Vector Char -> Int -> ([Int], [Int], [Int]) -> ([Int], [Int], [Int])
searchS' vec poi list@(rL, gL, bL)
    | poi == -1
    = list
    | otherwise
    = let c = vec VU.! poi
      in  case c of
              'R'       -> searchS' vec (poi - 1) ((poi) : rL, gL, bL)
              'G'       -> searchS' vec (poi - 1) (rL, (poi) : gL, bL)
              'B'       -> searchS' vec (poi - 1) (rL, gL, (poi) : bL)
              otherwise -> list


Measured memory_bytes: 5384