#include <bits/stdc++.h>
using namespace std;
const int inf = 0x3f3f3f3f;
const double eps = 1e-6;
const double pi = acos(-1.0);
int T[100005 << 2];
void update(int n, int L, int R, int p, int a) {
  if (L == R) {
    T[n] = a;
    return;
  }
  if (p > (L + R) / 2)
    update(n * 2 + 1, (L + R) / 2 + 1, R, p, a);
  else
    update(n * 2, L, (L + R) / 2, p, a);
  T[n] = max(T[n * 2], T[n * 2 + 1]);
}
int query(int n, int L, int R, int l, int r) {
  if (L == l && R == r) return T[n];
  int M = (L + R) / 2;
  if (l > M)
    return query(n * 2 + 1, M + 1, R, l, r);
  else if (r <= M)
    return query(n * 2, L, M, l, r);
  else
    return max(query(n * 2, L, M, l, M), query(n * 2 + 1, M + 1, R, M + 1, r));
}
struct node {
  node(){};
  node(int L, int R, int M, double P) : l(L), r(R), mx(M), p(P){};
  int l, r, mx;
  double p;
  vector<int> c;
  bool operator<(const node& n) const { return l == n.l ? r > n.r : l < n.l; };
} N[5005];
int q;
double dp[5005][5005];
double dfs(int n) {
  for (auto i : N[n].c) dfs(i);
  double a, b;
  dp[n][0] = 1.0 - N[n].p;
  for (auto i : N[n].c)
    if (N[n].mx - N[i].mx <= q) dp[n][0] *= dp[i][N[n].mx - N[i].mx];
  for (int j = 1; j <= q; ++j) {
    a = b = 1;
    for (auto i : N[n].c) {
      if (N[n].mx - N[i].mx + j - 1 <= q) a *= dp[i][N[n].mx - N[i].mx + j - 1];
      if (N[n].mx - N[i].mx + j <= q) b *= dp[i][N[n].mx - N[i].mx + j];
    }
    dp[n][j] = a * N[n].p + b * (1.0 - N[n].p);
  }
  if (n == 0) {
    double ans = dp[n][0] * N[n].mx;
    for (int j = 1; j <= q; ++j)
      if (dp[n][j] > dp[n][j - 1])
        ans += (dp[n][j] - dp[n][j - 1]) * (N[n].mx + j);
    return ans;
  } else
    return 0;
}
int main() {
  int n, a, l, r;
  double p;
  stack<int> s;
  cin >> n >> q;
  for (int i = 1; i <= n; ++i) {
    cin >> a;
    update(1, 1, n, i, a);
  }
  for (int i = 1; i <= q; ++i) {
    cin >> l >> r >> p;
    N[i] = node(l, r, query(1, 1, n, l, r), p);
  }
  N[0] = node(1, n, T[1], 0);
  sort(N + 1, N + 1 + q);
  s.push(0);
  for (int i = 1; i <= q; ++i) {
    while (!s.empty()) {
      l = N[s.top()].l;
      r = N[s.top()].r;
      if (l <= N[i].l && N[i].r <= r) {
        N[s.top()].c.push_back(i);
        s.push(i);
        break;
      } else
        s.pop();
    }
  }
  memset(dp, 0, sizeof(dp));
  printf("%.8lf\n", dfs(0));
}
