/* ******************************************************************************** */
#include <iostream> //
#include <cstdio> //
#include <cmath> //
#include <cstdlib> //
#include <cstring> //
#include <vector> //
#include <ctime> //
#include <deque> //
#include <queue> //
#include <algorithm> //
#include <map> //
#include <cmath> //
using namespace std; //
//
#define pb push_back //
#define mp make_pair //
#define X first //
#define Y second //
#define all(a) (a).begin(), (a).end() //
#define fillchar(a, x) memset(a, x, sizeof(a)) //
//
typedef pair< int , int > pii; //
typedef long long ll; //
typedef unsigned long long ull; //
//
#ifndef ONLINE_JUDGE //
void RI(vector< int >&a, int n){a.resize(n); for ( int i=0;i<n;i++) scanf ( "%d" ,&a[i]);} //
void RI(){} void RI( int &X){ scanf ( "%d" ,&X);} template < typename ...R> //
void RI( int &f,R&...r){RI(f);RI(r...);} void RI( int *p, int *q){ int d=p<q?1:-1; //
while (p!=q){ scanf ( "%d" ,p);p+=d;}} void print(){cout<<endl;} template < typename T> //
void print( const T t){cout<<t<<endl;} template < typename F, typename ...R> //
void print( const F f, const R...r){cout<<f<< ", " ;print(r...);} template < typename T> //
void print(T*p, T*q){ int d=p<q?1:-1; while (p!=q){cout<<*p<< ", " ;p+=d;}cout<<endl;} //
#endif // ONLINE_JUDGE //
template < typename T> bool umax(T&a, const T&b){ return b<=a? false :(a=b, true );} //
template < typename T> bool umin(T&a, const T&b){ return b>=a? false :(a=b, true );} //
template < typename T> //
void V2A(T a[], const vector<T>&b){ for ( int i=0;i<b.size();i++)a[i]=b[i];} //
template < typename T> //
void A2V(vector<T>&a, const T b[]){ for ( int i=0;i<a.size();i++)a[i]=b[i];} //
//
const double PI = acos (-1.0); //
const int INF = 1e9 + 7; //
//
/* -------------------------------------------------------------------------------- */
struct Edmonds {
const static int maxn = 1e2 + 7;
int n, m;
bool g[maxn][maxn];
bool vis[maxn];
int left[maxn];
void init( int n, int m) {
this ->n = n;
this ->m = m;
memset (g, 0, sizeof (g));
memset (left, -1, sizeof (left));
}
void add( int u, int v) {
g[u][v] = true ;
}
bool match( int u) {
for ( int v = 1; v <= m; v++) if (g[u][v] && !vis[v]) {
vis[v] = true ;
if (left[v] == -1 || match(left[v])) {
left[v] = u;
return true ;
}
}
return false ;
}
int solve() {
int ans = 0;
for ( int i = 1; i <= n; i++) {
memset (vis, 0, sizeof (vis));
if (match(i)) ans++;
}
return ans;
}
}; /** 点从1开始编号 **/
Edmonds solver;
int main() {
#ifndef ONLINE_JUDGE
freopen ( "in.txt" , "r" , stdin);
#endif // ONLINE_JUDGE
int n, m;
while (cin >> n, n) {
cin >> m;
solver.init(n, m);
for ( int i = 0; i < n; i ++) {
for ( int j = 0; j < m; j ++) {
int x;
scanf ( "%d" , &x);
if (x) solver.add(i + 1, j + 1);
}
}
cout << solver.solve() << endl;
}
return 0;
}
/* ******************************************************************************** */
|