Go: package main

import (
	"fmt"
)

func main() {
	var h, w int
	for {
		fmt.Scan(&w, &h)
		if w == 0 && h == 0 {
			return
		}
		matrix := make([][]int, h)
		Sean := make([][]bool, h)
		for i := 0; i < h; i++ {
			matrix[i] = make([]int, w)
			Sean[i] = make([]bool, w)
			for j := 0; j < w; j++ {
				fmt.Scan(&matrix[i][j])
			}
		}
		var count int
		for i := 0; i < h; i++ {
			for j := 0; j < w; j++ {
				if matrix[i][j] == 1 && Sean[i][j] == false {
					search(i, j, h, w, matrix, Sean)
					count++
				}
			}
		}
		fmt.Println(count)
	}
}
func search(x int, y int, h int, w int, matrix [][]int, Sean [][]bool) {
	if x < 0 || y < 0 || x >= h || y >= w || matrix[x][y] == 0 {
		return
	}
	if Sean[x][y] == true {
		return
	}

	Sean[x][y] = true

	search(x+1, y, h, w, matrix, Sean)
	search(x-1, y, h, w, matrix, Sean)
	search(x, y+1, h, w, matrix, Sean)
	search(x, y-1, h, w, matrix, Sean)
	search(x+1, y-1, h, w, matrix, Sean)
	search(x-1, y+1, h, w, matrix, Sean)
	search(x+1, y+1, h, w, matrix, Sean)
	search(x-1, y-1, h, w, matrix, Sean)
}

C++: #define _CRT_SECURE_NO_WARNINGS
#include "bits/stdc++.h"
#include <random>

using namespace std;

//呪文
#define DUMPOUT cerr
#define dump(...) DUMPOUT<<"  ";DUMPOUT<<#__VA_ARGS__<<" :["<<__LINE__<<":"<<__FUNCTION__<<"]"<<endl;DUMPOUT<<"    ";dump_func(__VA_ARGS__)

typedef unsigned uint; typedef long long ll; typedef unsigned long long ull; typedef pair<int, int> pii; typedef pair<ll, ll> pll; typedef pair<double, double> pdd; typedef pair<string, string> pss;
template <typename _KTy, typename _Ty> ostream& operator << (ostream& ostr, const pair<_KTy, _Ty>& m) { ostr << "{" << m.first << ", " << m.second << "}"; return ostr; }
template <typename _KTy, typename _Ty> ostream& operator << (ostream& ostr, const map<_KTy, _Ty>& m) { if (m.empty()) { ostr << "{ }"; return ostr; } ostr << "{" << *m.begin(); for (auto itr = ++m.begin(); itr != m.end(); itr++) { ostr << ", " << *itr; } ostr << "}"; return ostr; }
template <typename _Ty> ostream& operator << (ostream& ostr, const vector<_Ty>& v) { if (v.empty()) { ostr << "{ }"; return ostr; } ostr << "{" << v.front(); for (auto itr = ++v.begin(); itr != v.end(); itr++) { ostr << ", " << *itr; }	ostr << "}"; return ostr; }
template <typename _Ty> ostream& operator << (ostream& ostr, const set<_Ty>& s) { if (s.empty()) { ostr << "{ }"; return ostr; } ostr << "{" << *(s.begin()); for (auto itr = ++s.begin(); itr != s.end(); itr++) { ostr << ", " << *itr; }	ostr << "}"; return ostr; }
template <typename _Ty> ostream& operator << (ostream& ostr, const stack<_Ty>& s) { if (s.empty()) { ostr << "{ }"; return ostr; } stack<_Ty> t(s); ostr << "{" << t.top(); t.pop(); while (!t.empty()) { ostr << ", " << t.top(); t.pop(); } ostr << "}";	return ostr; }
template <typename _Ty> ostream& operator << (ostream& ostr, const list<_Ty>& l) { if (l.empty()) { ostr << "{ }"; return ostr; } ostr << "{" << l.front(); for (auto itr = ++l.begin(); itr != l.end(); ++itr) { ostr << ", " << *itr; } ostr << "}"; return ostr; }
template <typename _KTy, typename _Ty> istream& operator >> (istream& istr, pair<_KTy, _Ty>& m) { istr >> m.first >> m.second; return istr; }
template <typename _Ty> istream& operator >> (istream& istr, vector<_Ty>& v) { for (size_t i = 0; i < v.size(); i++) istr >> v[i]; return istr; }
namespace aux { // print tuple
	template<typename Ty, unsigned N, unsigned L> struct tp { static void print(ostream& os, const Ty& v) { os << get<N>(v) << ", "; tp<Ty, N + 1, L>::print(os, v); } };
	template<typename Ty, unsigned N> struct tp<Ty, N, N> { static void print(ostream& os, const Ty& value) { os << get<N>(value); } };
}
template<typename... Tys> ostream& operator<<(ostream& os, const tuple<Tys...>& t) { os << "{"; aux::tp<tuple<Tys...>, 0, sizeof...(Tys)-1>::print(os, t); os << "}"; return os; }

template<typename A, size_t N, typename T> inline void Fill(A(&array)[N], const T &val) { std::fill((T*)array, (T*)(array + N), val); }

void dump_func() { DUMPOUT << endl; }
template <class Head, class... Tail> void dump_func(Head&& head, Tail&&... tail) { DUMPOUT << head; if (sizeof...(Tail) == 0) { DUMPOUT << " "; } else { DUMPOUT << ", "; } dump_func(std::move(tail)...); }

#define PI 3.14159265358979323846
#define EPS 1e-11
#define FOR(i,a,b) for(int i=(a);i<(b);++i)
#define REP(i,n)  FOR(i,0,n)
#define all(x) (x).begin(), (x).end()
#define SZ(x) ((int)(x).size())
#define fake false



const int di[] = { 0, -1, -1, -1, 0, 1, 1, 1 };
const int dj[] = { 1, 1, 0, -1, -1, -1, 0, 1 };

int main()
{
	//clock_t start, end;
	//start = clock();

	cin.tie(0);
	ios::sync_with_stdio(false);

	while (true) {
		int w, h;
		cin >> w >> h;
		if (w == 0) break;

		vector<vector<int>> A(h, vector<int>(w));
		cin >> A;

		int cnt = 0;
		REP(i, h) REP(j, w) {
			if (A[i][j] == 1) {
				cnt++;

				queue<pii> qu;
				qu.push(pii(i, j));

				while (!qu.empty()) {
					pii p = qu.front(); qu.pop();
					int ii = p.first, jj = p.second;

					if (A[ii][jj] == 0) continue;
					A[ii][jj] = 0;

					REP(d, 8) {
						int ni = ii + di[d], nj = jj + dj[d];
						if (ni < 0 || h <= ni || nj < 0 || w <= nj || A[ni][nj] == 0) continue;
						qu.push(pii(ni, nj));
					}
				}

			}
		}
		cout << cnt << endl;
	}
	
	//end = clock();
	//printf("%d msec.\n", end - start);

	return 0;
}

C++: #include <bits/stdc++.h>
using namespace std;

typedef long long ll;
typedef unsigned long long ull;
typedef pair<ll, int> P;
typedef pair<ll, pair<ll, ll> > P3;

const ll MOD = ll(1e9 + 7);
const ll LLINF = LLONG_MAX;
const int IINF = INT_MAX;
const int MAX_N = int(1e5) + 5;
const double EPS = 1e-8;
int dx[] = {1, 0, -1, 0}, dy[] = {0, 1, 0, -1};
#define SORT(v) sort((v).begin(), (v).end())
#define SORTR(v) sort((v).rbegin(), (v).rend())
#define REP(i, n) for (int i = 0; i < n; i++)
#define REPR(i, n) for (int i = n; i >= 0; i--)
#define FOR(i, m, n) for (ll i = m; i < n; i++)

int a[55][55]{};
int h,w;

void dfs(int i, int j){
    a[i][j] = 0;
    for(int di = -1;di<=1;++di){
        for(int dj = -1; dj <= 1; ++dj){
            int ni = i+di, nj = j+dj;
            if(ni<0 || ni>=h)continue;
            if(nj<0 || nj>=w)continue;
            if(a[ni][nj]==0)continue;
            dfs(ni,nj);
        }
    }
}

int main() {
    while(1){
        cin >> w >> h;
        if(h==0 && w==0)break;
        REP(i,h)REP(j,w)cin >> a[i][j];
        int ans = 0;
        REP(i,h)REP(j,w)if(a[i][j]){
            dfs(i,j);
            ans++;
        }
        cout << ans << endl;
    }
    
    return 0;
}

C++: #include <bits/stdc++.h>
using namespace std;
int c[50][50];
bool vis[50][50];
int W,H;
void dfs(int x,int y) {
    vis[y][x]=1;
    for(int dx=-1;dx<=1;dx++) {
        for(int dy=-1;dy<=1;dy++) {
            int nx=x+dx,ny=y+dy;
            if(0>nx||nx>=W||0>ny||ny>=H||c[ny][nx]==0||vis[ny][nx]) continue;
            dfs(nx,ny);
        }
    }
}
int main() {
    while(scanf("%d %d",&W,&H),W) {
        for(int i=0;i<H;i++) {
            for(int j=0;j<W;j++) scanf("%d",&c[i][j]);
        }
        memset(vis,0,sizeof(vis));
        int ans=0;
        for(int i=0;i<H;i++) {
            for(int j=0;j<W;j++) {
                if(c[i][j]==1&&!vis[i][j]) {
                    dfs(j,i);
                    ans++;
                }
            }
        }
        printf("%d\n",ans);
    }
}