#include <algorithm>
#include <iostream>
#include <vector>
#include <cstdio>

using namespace std;

vector<vector<int>> graph, graph_rev, new_graph;
vector<int> weak, strong, sorted;
vector<bool> used;

long long min(long long a, long long b) {
    return (a > b) ? b : a;
}
long long max(long long a, long long b) {
    return (a > b) ? a : b;
}

void dfs_weak(int u, int cnt) {
    weak[u] = cnt;
    used[u] = true;
    for (int v : graph[u]) {
        if (!used[v]) {
            dfs_weak(v, cnt);
        }
    }
    for (int v : graph_rev[u]) {
        if (!used[v]) {
            dfs_weak(v, cnt);
        }
    }
}

void dfs_strong(int u) {
    used[u] = true;

    for (int v : graph[u]) {
        if (!used[v]) {
            dfs_strong(v);
        }
    }
    sorted.push_back(u);
}

void dfs_revert(int u, int cnt) {
    used[u] = true;
    strong[u] = cnt;
    for (int v : graph_rev[u]) {
        if (!used[v]) {
            dfs_revert(v, cnt);
        }
    }
}

bool cmp(const pair<int, int>& a, const pair<int, int> & b) {
    return a.second < b.second or (a.second == b.second and a.first < b.first);
}

int main() {
    freopen("robots.in", "r", stdin);
    freopen("robots.out", "w", stdout);
    int n, m, g;
    cin >> n >> m >> g;
    graph.resize(n * m);
    graph_rev.resize(n * m);
    weak.resize(n * m);
    strong.resize(n * m);
    vector<bool> colored(n * m, false);
    char c[1179];
    for (int i = 0; i < n; i++) {
        scanf("%s", c);
        for (int j = 0; j < m; j++) {
            int u = i * m + j;
            if (c[j] == 'e' or c[j] == 'E') {
                graph[u].push_back(u + 1);
                graph_rev[u + 1].push_back(u);
            }
            if (c[j] == 'w' or c[j] == 'W') {
                graph[u].push_back(u - 1);
                graph_rev[u - 1].push_back(u);
            }
            if (c[j] == 'N' or c[j] == 'n') {
                graph[u].push_back(u - m);
                graph_rev[u - m].push_back(u);
            }
            if (c[j] == 'S' or c[j] == 's') {
                graph[u].push_back(u + m);
                graph_rev[u + m].push_back(u);
            }
            if (c[j] == 'S' or c[j] == 'E' or c[j] == 'W' or c[j] == 'N') {
                colored[u] = true;
            }
        }
    }
    used.assign(n * m, 0);
    int cnt = 0;
    for (int i = 0; i < n * m; i++) {
        if (!used[i]) {
            dfs_weak(i, cnt++);
        }
    }
    vector<vector<int> > weak_components(cnt);
    for (int i = 0; i < n * m; i++) {
        weak_components[weak[i]].push_back(i);
    }
    used.assign(n * m, 0);
    cnt = 0;
    for (int i = 0; i < n * m; i++) {
        if (!used[i]) {
            dfs_strong(i);
        }
    }
    reverse(sorted.begin(), sorted.end());
    used.assign(n * m, 0);
    for (int u : sorted) {
        if (!used[u]) {
            dfs_revert(u, cnt++);
        }
    }
    vector<vector<int> > strong_components(cnt);
    for (int i = 0; i < n * m; i++) {
        strong_components[strong[i]].push_back(i);
    }
    int ans = 0;
    vector<int> anses(weak_components.size());
    for (int i = 0; i < cnt; i++) {
        if ((int)strong_components[i].size() > 1) {
            int c_am = 0;
            for (int j : weak_components[weak[strong_components[i][0]]]) {
                c_am += colored[j];
            }
            ans += min(c_am, strong_components[i].size());
            anses[weak[strong_components[i][0]]] = min(c_am, strong_components[i].size());
        }
    }
    cout << ans << endl;
    if (g) {
        new_graph.resize(cnt);
        for (int i = 0; i < n * m; i++) {
            new_graph[strong[i]].push_back(strong[graph[i][0]]);
        }
        vector<int> centers;
        for (int i = 0; i < cnt; i++) {
            sort(new_graph[i].begin(), new_graph[i].end());
            new_graph[i].resize(distance(new_graph[i].begin(), unique(new_graph[i].begin(), new_graph[i].end())));
            if ((int)strong_components[i].size() > 1) {
                centers.push_back(i);
            }
        }
        vector<int> new_colored(cnt, 0);
        for (int i = 0; i < n * m; i++) {
            new_colored[strong[i]] += colored[i];
        }
        vector<vector<int> > chosen(weak_components.size());
        for (int i = 0; i < n * m; i++) {
            if (colored[i] and (int)chosen[weak[i]].size() < anses[weak[i]]) {
                chosen[weak[i]].push_back(i);
            }
        }
        vector<vector<int> > destination(weak_components.size());
        vector<vector<int> > length(weak_components.size());
        vector<vector<int> > binup(20, vector<int>(n * m));
        
        for (int i = 0; i < n * m; i++) {
            binup[0][i] = graph[i][0];
        }
        for (int i = 1; i < 20; i++) {
            for (int j = 0; j < n * m; j++) {
                binup[i][j] = binup[i - 1][binup[i - 1][j]];
            }
        }
        vector<vector<pair<int, int> > > from_destination(n * m);
        for (int i = 0; i < (int)chosen.size(); i++) {
            destination[i].resize(chosen[i].size());
            length[i].resize(chosen[i].size());
            for (int j = 0; j < (int)chosen[i].size(); j++) {
                destination[i][j] = chosen[i][j];

                for (int k = 19; k >= 0; k--) {
                    if (strong_components[strong[binup[k][destination[i][j]]]].size() == 1) {
                        destination[i][j] = binup[k][destination[i][j]];
                        length[i][j] += 1 << k;
                    }
                }
                if (strong_components[strong[destination[i][j]]].size() == 1) {
                    destination[i][j] = graph[destination[i][j]][0];
                    length[i][j]++;
                }
                from_destination[destination[i][j]].push_back(make_pair(chosen[i][j], length[i][j]));
            }
        }
        for (int i = 0; i < n * m; i++) {
            sort(from_destination[i].begin(), from_destination[i].end(), cmp);
        }
        vector<pair<int, int> > full_answer;
        int t = 1e4;
        for (int i = 0; i < (int)centers.size(); i++) {
            int u = strong_components[centers[i]][0];
            int begin = u;
            do {
                for (pair<int, int> v : from_destination[u]) {
                    full_answer.push_back(make_pair(v.first, t - v.second));
                    t++;
                }
                if (!from_destination[u].empty())
                    t--;
                t += 2;
        //        cout << u << endl;
                u = graph[u][0];
            } while (u != begin);
        }
        for (int i = 0; i < (int)full_answer.size(); i++) {
            cout << full_answer[i].first / m + 1 << ' ' << full_answer[i].first % m + 1 << ' ' << full_answer[i].second << endl;
            //cerr << full_answer[i].first << ' ' << full_answer[i].second << endl;
        }
    }
}
