#include <bits/stdc++.h>

template <typename T>
T BinarySearch(T lo, T hi, std::function<bool(T)> pred) {
  while (lo + 1 < hi) {
    T mid = (hi - lo) / 2 + lo;
    if (pred(mid)) {
      lo = mid;
    } else {
      hi = mid;
    }
  }
  return lo;
}

template <typename T>
class BIT {
 public:
  BIT(int n) : v_(n) {}
  T Sum(int i) const {
    T ret = 0;
    while (i >= 0) {
      ret += v_[i];
      i = (i & (i + 1)) - 1;
    }
    return ret;
  }
  T Get(int i) const { return Sum(i) - Sum(i - 1); }
  void Add(int i, T v) {
    while (i < v_.size()) {
      v_[i] += v;
      i |= i + 1;
    }
  }

 private:
  std::vector<T> v_;
};

// #undef DEBUG
#if DEBUG
template <typename T>
void debug(const T& value) {
  std::cerr << value;
}
template <typename T, typename... Ts>
void debug(const T& value, const Ts&... args) {
  std::cerr << value << ", ";
  debug(args...);
}
#define dbg(...)                        \
  do {                                  \
    cerr << #__VA_ARGS__ << ": ";       \
    debug(__VA_ARGS__);                 \
    cerr << " (L" << __LINE__ << ")\n"; \
  } while (0)
#else
#define dbg(...)
#endif

void read_from_cin() {}
template <typename T, typename... Ts>
void read_from_cin(T& value, Ts&... args) {
  std::cin >> value;
  read_from_cin(args...);
}
#define rd(type, ...) \
  type __VA_ARGS__;   \
  read_from_cin(__VA_ARGS__);

template <typename T>
void write_to_cout(const T& value) {
  std::cout << value << '\n';
}
template <typename T, typename... Ts>
void write_to_cout(const T& value, const Ts&... args) {
  std::cout << value << ' ';
  write_to_cout(args...);
}
#define wt(...) write_to_cout(__VA_ARGS__);

#define all(x) (x).begin(), (x).end()
#define rep(i, n) for (int i = 0; i < (int)(n); ++i)

using ll = long long;

template <typename T>
using V = std::vector<T>;
template <typename T>
using VV = V<V<T>>;

using namespace std;

int main() {
  ios_base::sync_with_stdio(false);
  cin.tie(NULL);

  rd(int, n);

  V<string> s(n);
  rep(i, n) {
    cin >> s[i];
    reverse(all(s[i]));
  }
  sort(all(s));

  for (auto si : s) dbg(si);

  V<pair<int, int>> len(n);
  rep(i, n) len[i] = {s[i].size(), i};
  sort(all(len), greater());

  for (auto [a, b] : len) dbg(a, b);

#ifdef DEBUG
  ll very_naive = 0;
  rep(i, n) rep(j, i) {
    auto check = [](const string &a, const string &b) {
      string prefix = a.substr(0, a.size() - 1);
      if (b.substr(0, prefix.size()) != prefix) {
        return false;
      }
      for (int i = a.size() - 1; i < b.size(); ++i) {
        if (b[i] == a.back()) {
          return true;
        }
      }
      return false;
    };
    assert(check("xyc", "xyxcba"));
    assert(check("b", "cba"));
    assert(check("a", "cba"));
    assert(check("c", "cba"));
    assert(check("b", "ba"));
    assert(check("a", "ba"));
    if (check(s[i], s[j]) || check(s[j], s[i])) {
      ++very_naive;
    }
  }
#endif

  ll ans = 0;
  for (char alpha = 'a'; alpha <= 'z'; ++alpha) {
    auto lit = len.begin();
    set<int> avail_set;
    BIT<int> avail(n);
    auto add = [&](int i) {
      if (avail_set.insert(i).second) {
        avail.Add(i, 1);
      }
    };
    set<int> longer;
    for (int cl = len[0].first; cl >= 1; --cl) {
      for (int i : longer) {
        if (s[i][cl - 1] == alpha) add(i);
      }
      set<int> same;
      while (lit != len.end() && lit->first == cl) {
        same.insert(lit->second);
        ++lit;
      }
      for (int i : same) {
        if (s[i][cl - 1] == alpha) {
          string prefix = s[i].substr(0, cl - 1);

#ifdef DEBUG
          int naive = 0;
          for (int j = 0; j < n; ++j) {
            if (s[j].substr(0, cl - 1) == prefix) {
              if (avail.Get(j)) {
                ++naive;
                // dbg(prefix, i, j, avail.Get(j));
              }
            }
          }
#endif

          int fast;
          auto match = [&](int k) {
            const string &si = s[k];
            if (si.size() < prefix.size()) return false;
            for (int j = prefix.size() - 1; j >= 0; --j) {
              if (si[j] != prefix[j]) return false;
            }
            return true;
          };
          int lo, hi;
          {
            int ok = i, ng = -1;
            while (ok - ng > 1) {
              int mid = (ok + ng) / 2;
              (match(mid) ? ok : ng) = mid;
            }
            lo = ok;
          }
          {
            int ok = i, ng = n;
            while (ng - ok > 1) {
              int mid = (ok + ng) / 2;
              (match(mid) ? ok : ng) = mid;
            }
            hi = ok;
          }
          fast = avail.Sum(hi) - avail.Sum(lo - 1);
          /*
          if (cl > 1) {
            int j = BinarySearch<int>(i, n, [&](int k) {
              const string &si = s[k];
              if (si.size() < prefix.size()) return false;
              for (int j = prefix.size() - 1; j >= 0; --j) {
                if (si[j] != prefix[j]) return false;
              }
              return true;
            });
            // dbg(prefix, i, j, avail.Get(j));
            fast = avail.Sum(j) - avail.Sum(i);
          } else {
            fast = avail_set.size();
            // fast = avail.Sum(n - 1) - 1;
            // fast = avail.Sum(i - 1);
          }
          */

#ifdef DEBUG
          if (naive != fast) {
            dbg(cl, naive, fast, s[i], alpha);
          }
          assert(naive == fast);
#endif
          ans += fast;
        }
      }
      for (int i : same) {
        if (s[i][cl - 1] == alpha) add(i);
        longer.insert(i);
      }
    }
  }
#ifdef DEBUG
  if (very_naive != ans) {
    dbg(very_naive, ans);
    assert(false);
  }
#endif
  wt(ans);
}


Measured memory_bytes: 23884