#include <bits/stdc++.h>
using namespace std;
int myd[26][26];
const int maxm = 2007, maxn = 107, INF = 1e9;
struct edge {
  int from, to, flow, cap;
  edge(){};
  edge(int u, int v, int c, int f) : from(u), to(v), cap(c), flow(f) {}
} e[maxm * 2];
vector<int> g[maxn];
int n, m, s, t, cnt;
int d[maxn], cur[maxn];
void addedge(int u, int v, int c) {
  e[cnt] = edge(u, v, c, 0);
  g[u].push_back(cnt++);
  e[cnt] = edge(v, u, 0, 0);
  g[v].push_back(cnt++);
}
bool bfs() {
  memset(d, 0, sizeof(d));
  memset(cur, 0, sizeof(cur));
  queue<int> q;
  d[s] = 1;
  q.push(s);
  while (!q.empty()) {
    int now = q.front();
    q.pop();
    int len = g[now].size();
    for (int i = 0; i < len; ++i) {
      int x = g[now][i];
      int cap = e[x].cap, flow = e[x].flow, to = e[x].to;
      if (!d[to] && flow < cap) {
        d[to] = d[now] + 1;
        q.push(to);
      }
    }
  }
  return d[t];
}
int dfs(int now, int a) {
  if (now == t || a == 0) return a;
  int tot = 0, f, len = g[now].size();
  for (int& i = cur[now]; i < len; ++i) {
    int x = g[now][i];
    int to = e[x].to;
    if (d[now] + 1 == d[to] &&
        (f = dfs(to, min(a, e[x].cap - e[x].flow))) > 0) {
      e[x].flow += f;
      e[x ^ 1].flow -= f;
      tot += f;
      a -= f;
      if (!a) break;
    }
  }
  return tot;
}
int maxflow() {
  int flow = 0;
  while (bfs()) {
    flow += dfs(s, INF);
  }
  return flow;
}
void init() {
  cnt = 0;
  for (int i = 1; i < maxn; ++i) g[i].clear();
}
int main() {
  int i, j, k;
  while (scanf("%d%d", &n, &m) != EOF) {
    init();
    for (i = 0; i < m; ++i) {
      int u, v, c;
      scanf("%d%d%d", &u, &v, &c);
      addedge(u, v, c);
      addedge(v, u, c);
      myd[u][v] = c;
      myd[v][u] = c;
    }
    s = 1;
    t = n;
    int ans = maxflow();
    int maxv = 0;
    for (i = 1; i <= n; ++i) {
      for (j = 1; j <= n; ++j) {
        if (d[i] > 0 && d[j] == 0) {
          maxv = max(maxv, myd[i][j]);
        }
      }
    }
    printf("%d\n", ans);
  }
  return 0;
}
