#include <bits/stdc++.h>
using namespace std;
const int maxn = 35005;
struct Node {
  int l, r;
  int lazy;
  int Max;
} node[maxn << 2];
int n, k;
int a[maxn];
int pre[maxn];
int dp[maxn];
void push_down(int root) {
  node[root << 1].lazy += node[root].lazy;
  node[root << 1 | 1].lazy += node[root].lazy;
  node[root << 1].Max += node[root].lazy;
  node[root << 1 | 1].Max += node[root].lazy;
  node[root].lazy = false;
}
void push_up(int root) {
  node[root].Max = max(node[root << 1].Max, node[root << 1 | 1].Max);
}
void build(int l, int r, int root) {
  node[root].l = l, node[root].r = r;
  node[root].lazy = 0;
  if (l == r) {
    node[root].Max = dp[l];
    return;
  }
  int mid = (l + r) >> 1;
  build(l, mid, root << 1);
  build(mid + 1, r, root << 1 | 1);
  push_up(root);
}
void update(int l, int r, int root) {
  if (node[root].l >= l && node[root].r <= r) {
    node[root].lazy += 1;
    node[root].Max += 1;
    return;
  }
  if (node[root].lazy) push_down(root);
  int mid = (node[root].l + node[root].r) >> 1;
  if (l <= mid) update(l, r, root << 1);
  if (r > mid) update(l, r, root << 1 | 1);
  push_up(root);
}
int query(int l, int r, int root) {
  if (node[root].l >= l && node[root].r <= r) {
    return node[root].Max;
  }
  if (node[root].lazy) push_down(root);
  int t1 = 0, t2 = 0;
  int mid = (node[root].l + node[root].r) >> 1;
  if (l <= mid) t1 = query(l, r, root << 1);
  if (r > mid) t2 = query(l, r, root << 1 | 1);
  push_up(root);
  if (t1 > t2) return t1;
  return t2;
}
int main() {
  scanf("%d%d", &n, &k);
  for (int i = 1; i <= n; i++) scanf("%d", &a[i]);
  memset(dp, 0, sizeof(dp));
  for (int i = 1; i <= k; i++) {
    build(0, n, 1);
    for (int j = 0; j < maxn; j++) pre[j] = 0;
    for (int j = 1; j <= n; j++) {
      update(pre[a[j]], j - 1, 1);
      pre[a[j]] = j;
      dp[j] = query(0, j - 1, 1);
    }
  }
  printf("%d\n", dp[n]);
  return 0;
}
