import std.algorithm;
import std.array;
import std.ascii;
import std.container;
import std.conv;
import std.math;
import std.numeric;
import std.range;
import std.stdio;
import std.string;
import std.typecons;

void log(A...)(A arg) {
    stderr.writeln(arg);
}
int size(T)(in T s) {
    return cast(int)s.length;
}

void main() {
    int H, W; scanf("%d %d\n", &H, &W);
    auto F = new string[H];
    foreach (ref a; F) a = readln.chomp;
    F.reverse;

    int ans = 0;
    foreach (int y; 0 .. H) {
        foreach (int x; 0 .. W) {
            int dx = 1;
            int nx = x + dx;
            if (nx < 0 || nx >= W) continue;
            if (F[y][x] == F[y][nx]) ans++;
        }
    }

    int INF = 1<<28;

    auto cur_state = new int[W];
    foreach (i; 0 .. H * W) {
        auto cost = new int[W];
        foreach (int x; 0 .. W) {
            int calc() {
                int c = 0;
                for (int dx = -1; dx <= 1; dx += 2) {
                    int nx = x + dx;
                    if (nx < 0 || nx >= W) continue;
                    for (int y = 0; y < H - 1; y++) {
                        int ny = y - cur_state[nx];
                        int cy = y - cur_state[x];
                        if (cy < 0) continue;
                        if (ny - 1 < 0) continue;
                        if (F[cy + 1][x] == F[ny][nx]) {
                            c++;
                        }
                    }
                }
                return c;
            }
            if (cur_state[x] == H) cost[x] = INF;
            else cost[x] = calc();
        }
        auto d = cost.length - minPos(cost).length;
        //log(cost, " ", d, " ", cur_state, " ", cost[d]);
        ans += cost[d];
        cur_state[d]++;
    }
    writeln(ans);
}
