#include <bits/stdc++.h>
#define GET_MACRO(_1,_2,_3,_4,_5,_6,NAME,...) NAME
#define pr(...) cerr<< GET_MACRO(__VA_ARGS__,pr6,pr5,pr4,pr3,pr2,pr1)(__VA_ARGS__) <<endl
#define pr1(a) (#a)<<"="<<(a)<<" "
#define pr2(a,b) pr1(a)<<pr1(b)
#define pr3(a,b,c) pr1(a)<<pr2(b,c)
#define pr4(a,b,c,d) pr1(a)<<pr3(b,c,d)
#define pr5(a,b,c,d,e) pr1(a)<<pr4(b,c,d,e)
#define pr6(a,b,c,d,e,f) pr1(a)<<pr5(b,c,d,e,f)
#define pr7(a,b,c,d,e,f,g) pr1(a)<<pr6(b,c,d,e,f,g)
#define pr8(a,b,c,d,e,f,g,h) pr1(a)<<pr7(b,c,d,e,f,g,h)
using namespace std;
using Int = long long;
using ll = long long;
using Double = long double;
const Int INF = (1LL<<55)+1e9; // ~ 3.6 * 1e16
const Double EPS = 1e-8;
const Double PI = 6.0 * asin((Double)0.5);
using P = pair<Int,Int>;
using T = tuple<Int,Int,Int>;
template<class T> T Max(T &a,T b){return a=max(a,b);}
template<class T> T Min(T &a,T b){return a=min(a,b);}
ostream& operator<<(ostream& o,P p){return o<<"("<<p.first<<","<<p.second<<")";}
ostream& operator<<(ostream& o,T t){return o<<"("<<get<0>(t)<<","<<get<1>(t)<<","<<get<2>(t)<<")";}
istream& operator>>(istream& i,P &p){return i>>p.first>>p.second;}
ostream& operator<<(ostream& o,vector<auto> &a){Int i=0;for(auto t:a)o<<(i++?" ":"")<<t;return o;}
istream& operator>>(istream& i,vector<auto> &a){for(auto &t:a)i>>t;return i;}
void prArr(auto a,string s=" "){Int i=0;for(auto t:a)cout<<(i++?s:"")<<t;cout<<endl;}
const Int N = 300000;

constexpr ll mod_pow(ll x, ll n, Int mod){
  return n == 0? 1:(n%2? x:1) * mod_pow((x*x)%mod,n/2, mod) % mod;
}  

constexpr ll mod_inv(Int num,Int mod){return mod_pow(num, mod-2, mod);}
const ll mod[] = {1000000007,1000000009,1000000021};
const ll B[]= {1777771,10000019,10000079};
const ll inv[] = {mod_inv(B[0],mod[0]), mod_inv(B[1],mod[1]),mod_inv(B[2],mod[2])};

class Hash{
public:

  ll num;
  ll idx;
  vector<ll> K;
  Int b;
  Hash(Int b):b(b){
    K.resize(N);
    K[0] = 1;
    for(Int i=1;i<N;i++) K[i] = K[i-1] * B[b] % mod[b];
    num = 0;
    idx = K[N/2];
  }

  void inc(){num = (num + idx) % mod[b];}
  void dec(){num = (num - idx + mod[b]) % mod[b];}
  void moveLeft(){idx = idx * inv[b] % mod[b];}
  void moveRight(){idx = idx * B[b] % mod[b];}
  
};


signed main(){
  cin.tie(0);
  ios_base::sync_with_stdio(0);
  cout << fixed << setprecision(12);

  Int n;
  cin>>n;
  string s;
  cin>>s;

  vector<map<ll,Int> > cnt(3);
  vector<Hash> hash{Hash(0), Hash(1), Hash(2)};
  vector<Hash> hash2 = hash;
  
  for(Int k = 0; k<n ; k++){
    char ch = s[k];
    for(Int i=0;i<3;i++){
      auto &A = hash[i];
      if(ch == '+') A.inc();
      if(ch == '-') A.dec();
      if(ch == '<') A.moveLeft();
      if(ch == '>') A.moveRight();
      cnt[i][A.num]++;
    }
  }

  vector<ll> allHash(3);
  vector<ll> Ofset(3,0);
  for(Int i=0;i<3;i++) allHash[i] = hash[i].num;
  
  Int ans = 0;
  for(Int k=0;k<n;k++){
    
    char ch = s[k];
    Int mn = INF;
    for(Int i=0;i<3;i++){
      auto &A = hash2[i];
      auto &U = allHash[i];
      auto &X = Ofset[i];
      ll val = (U - X + mod[i]) % mod[i];
      Min(mn, cnt[i][val]);
      //pr(U, X, (U + X)%mod[i], A.num);
      if(ch == '+') X = (X - A.idx + mod[i]) % mod[i], A.inc();
      if(ch == '-') X = (X + A.idx + mod[i]) % mod[i], A.dec();
      if(ch == '>') U = U * B[i] % mod[i], A.moveRight();
      if(ch == '<') U = U * inv[i] % mod[i], A.moveLeft();
      assert(cnt[i][A.num] != 0);
      cnt[i][A.num]--;
    }
    ans += mn;
  }
  cout<<ans<<endl;
  
  
  return 0;
}


Measured memory_bytes: 108316