Go: package main

import (
	"bufio"
	"os"
	"strconv"
	"strings"
		"reflect"
	"fmt"
)

var scanner = bufio.NewScanner(os.Stdin)

func main() {
	// 上面の色を固定してから、左右方向に回転して一致するものがあるかを調べる
	round := [][]int{
		{1,2,3,4,5,6}, {1,3,5,2,4,6}, {1,4,2,5,3,6}, {1,5,4,3,2,6}, // c1を上面に固定して回転
		{2,6,3,4,1,5}, {2,3,1,6,4,5}, {2,1,4,3,6,5}, {2,4,6,1,3,5}, // c2を上面に固定して回転
		{3,1,2,5,6,4}, {3,2,6,1,5,4}, {3,5,1,6,2,4}, {3,6,5,2,1,4}, // c3を上面に固定して回転
		{4,1,5,2,6,3}, {4,2,1,6,5,3}, {4,5,6,1,2,3}, {4,6,2,5,1,3}, // c4を上面に固定して回転
		{5,1,3,4,6,2}, {5,3,6,1,4,2}, {5,4,1,6,3,2}, {5,6,4,3,1,2}, // c5を上面に固定して回転
		{6,2,4,3,5,1}, {6,3,2,5,4,1}, {6,5,3,4,2,1}, {6,4,5,2,3,1}, // c6を上面に固定して回転

	}
	for scanner.Scan() {
		n, _ := strconv.Atoi(scanner.Text())
		if n == 0 {
			break
		}
		cubes := make([][]string, n)
		for i := 0; i < n; i++ {
			scanner.Scan()
			cubes[i] = strings.Split(scanner.Text(), " ")
		}
		check := func(a, b int) bool {
			tmp := make([]string, 6)
			for i := 0; i < 24; i++ {
				for j := 0; j < 6; j++ {
					tmp[j] = cubes[b][round[i][j]-1]
				}
				if reflect.DeepEqual(tmp, cubes[a]) {
					return true
				}
			}
			return false
		}
		tbl := make([]int, n)
		// 全ての組み合わせを調べる
		for i := 0; i < n; i++ {
			if tbl[i] == 1 {
				continue
			}
			for j := i+1; j < n; j++ {
				if check(i, j) {
					tbl[j] = 1
				}
			}
		}
		fmt.Println(sum(tbl))
	}
}

func sum(a []int) int {
	ret := 0
	for _, v := range a {
		ret += v
	}
	return ret
}

C++: #include<iostream>
#include<algorithm>
#include<vector>
#include<queue>
#define lol(i,n) for(int i=0;i<n;i++)
#define mod 1000000007
typedef long long ll;
using namespace std;
string s[50][6];
int d[12][6]={
  {0,1,2,3,4,5},
  {0,2,3,4,1,5},
  {0,3,4,1,2,5},
  {0,4,1,2,3,5},
  
  {0,1,2,3,4,5},
  {2,1,3,4,0,5},
  {3,1,4,0,2,5},
  {4,1,0,2,3,5},
  
  {0,1,2,3,4,5},
  {1,4,2,3,5,0},
  {4,5,2,3,0,1},
  {5,0,2,3,1,4}
};
int main(){
  int n;
  while(cin>>n&&n){
    int ans=0;
    lol(i,n){
      lol(j,6)cin>>s[i][j];
      bool same=false;
      lol(j,i){
	lol(r,12){
	  bool ok=true;
	  lol(k,6){
	    if(s[i][k]!=s[j][d[r][k]])ok=false;
	  }
	  if(ok)same=true;
	}
      }
      if(same)ans++;
    }
    cout<<ans<<endl;
  }
  return 0;
}

C++: #include <iostream>
#include <string>
#include <vector>
#include <algorithm>
using namespace std;

enum FACE { TOP, BOTTOM, FRONT, BACK, LEFT, RIGHT };

class UnionFind
{
public:
	vector<int> data;
	UnionFind(int size):data(size, -1){}
	
	bool unionSet(int x, int y)
	{
		x = root(x); y=root(y);
		if(x != y)
		{
			if(data[y] < data[x]) swap(x, y);
			data[x] += data[y]; data[y] = x;
		}
		return x != y;
	}
	
	int root(int x)
	{
		return data[x] < 0 ? x:data[x]=root(data[x]);
	}
};

class Dice
{
public:
	Dice(string m[6])
	{
		f[TOP]=0; f[FRONT]=1; f[LEFT]=2;
		f[RIGHT]=3; f[BACK]=4; f[BOTTOM]=5;
		
		for(int i=0; i<6; i++)
			val[i]=m[i];
	}
	
	void rotated(FACE a, FACE b, FACE c, FACE d)
	{
		int tmp = f[a];
		f[a]=f[b];
		f[b]=f[c];
		f[c]=f[d];
		f[d]=tmp;
	}
	
	vector<Dice> all_rotate()
	{
		vector<Dice> t;
		for(int i=0; i<6; (i&1?rotateY():rotateX()), i++)
		for(int j=0; j<4; rotateZ(), j++)
			t.push_back(*this);
			
		return t;
	}
	
	void rotateX() { rotated(TOP, BACK, BOTTOM, FRONT); }
	void rotateY() { rotated(TOP, LEFT, BOTTOM, RIGHT); }
	void rotateZ() { rotated(FRONT, RIGHT, BACK, LEFT); }
	
	string GetVal(FACE fe) { return val[f[fe]]; }

	
	int f[6];
	string val[6];
};

bool isequal(vector<Dice>& a, vector<Dice>& b)
{
	for(int k=0; k<a.size(); k++) 
	for(int j=0; j<b.size(); j++)
	{
		bool g=true;
		for(int i=0; i<6; i++)
		{
			if(a[k].GetVal(i)!=b[j].GetVal(i))
			{
				g=false;
				break;
			}
		}
		if(g) return true;
	}
	
	return false;
}

int main()
{
	int N;
	while(cin >> N, N)
	{
		vector<Dice> d;
		for(int i=0; i<N; i++)
		{
			string s[6];
			for(int j=0; j<6; j++)
				cin >> s[j];
				
			d.push_back(s);
		}
		
		vector<vector<Dice> > face;
		for(int i=0; i<d.size(); i++)
			face.push_back(d[i].all_rotate());
		
		int ans=0;
		UnionFind uf(N);
		
		for(int i=0; i<N; i++)
		for(int j=i+1; j<N; j++)
		{
			if(i==j) continue;
			if(isequal(face[j], face[i]))
			{
				if(uf.unionSet(i,j))
					ans++;
			}
		}
		
		cout << ans << endl;
	}
}

C++: #include <iostream>
#include <cstdio>
#include <algorithm>
#include <vector>
#include <sstream>
#include <cmath>
#include <queue>

using namespace std;

bool check[6][6][6][6][6][6];

int index(string str){
	if(str == "Cyan"){
		return 0;
	}else if(str == "Yellow"){
		return 1;
	}else if(str == "Red"){
		return 2;
	}else if(str == "Magenta"){
		return 3;
	}else if(str == "Green"){
		return 4;
	}else{
		return 5;
	}
}

void rotate_1(int col[6]){
	int dummy = col[1];
	col[1] = col[2];
	col[2] = col[4];
	col[4] = col[3];
	col[3] = dummy;
}

void rotate_2(int col[6]){
	int dummy = col[3];
	col[3] = col[0];
	col[0] = col[2];
	col[2] = col[5];
	col[5] = dummy;
}

void rotate_3(int col[6]){
	int dummy = col[0];
	col[0] = col[1];
	col[1] = col[5];
	col[5] = col[4];
	col[4] = dummy;
}

void fill_rotate(int col[6]){
	for(int i = 0; i < 4; i++){
		for(int j = 0; j < 4; j++){
			rotate_2(col);
			check[col[0]][col[1]][col[2]][col[3]][col[4]][col[5]] = true;
			for(int piyo = 0; piyo < 6; piyo++){
				//cout << col[piyo] << " ";
			}
			//cout << endl;
		}
		rotate_1(col);
	}
	rotate_3(col);
	for(int i = 0; i < 4; i++){
		rotate_2(col);
		check[col[0]][col[1]][col[2]][col[3]][col[4]][col[5]] = true;
			for(int piyo = 0; piyo < 6; piyo++){
				//cout << col[piyo] << " ";
			}
			//cout << endl;
	}
	rotate_3(col);
	rotate_3(col);
	for(int i = 0; i < 4; i++){
		rotate_2(col);
		check[col[0]][col[1]][col[2]][col[3]][col[4]][col[5]] = true;
			for(int piyo = 0; piyo < 6; piyo++){
				//cout << col[piyo] << " ";
			}
			//cout << endl;
	}
}

int main(){
	
	int n;
	
	while(true){
		
		cin >> n;
		
		if(n == 0){
			break;
		}
		
		int col[6];
		
		for(int i = 0; i < 6; i++){
		for(int j = 0; j < 6; j++){
		for(int k = 0; k < 6; k++){
		for(int l = 0; l < 6; l++){
		for(int m = 0; m < 6; m++){
		for(int n = 0; n < 6; n++){
			check[i][j][k][l][m][n] = false;
		}}}}}}
		
		int ans = 0;
		
		for(int loop = 0; loop < n; loop++){
			for(int i = 0; i < 6; i++){
				string str;
				cin >> str;
				col[i] = index(str);
			}
			
			if(!check[col[0]][col[1]][col[2]][col[3]][col[4]][col[5]]){
				ans++;
				fill_rotate(col);
			}
		}
		
		cout << n - ans << endl;
		
	}
	
	return 0;
}

C++: #include <iostream>
#include <string>

using namespace std;

class Box{
public:
	string c1,c2,c3,c4,c5,c6;

	bool operator==( const Box& lhs ){
		return c1 == lhs.c1 && c2 == lhs.c2 && c3 == lhs.c3 && c4 == lhs.c4 && c5 == lhs.c5 && c6 == lhs.c6;
	}

	void rotatet(){
		string d1,d2;
		d1 = c1;
		c1 = c5;
		d2 = c2;
		c2 = d1;
		c5 = c6;
		c6 = d2;
	}

	void rotatey(){
		string d1,d2;
		d1 = c1;
		c1 = c3;
		d2 = c4;
		c4 = d1;
		c3 = c6;
		c6 = d2;
	}
};


int main( void )
{
	int n;
	Box box[31];
	bool check[31];

	while( cin >> n && n != 0 ){
		for( int i = 0;i < 31;i++ ) check[i] = false;
		for( int i = 0;i < n;i++ ){
			cin >> box[i].c1 >>  box[i].c2 >>  box[i].c3 >>  box[i].c4 >>  box[i].c5 >>  box[i].c6; 
		}

		int count = 0;

		for( int i = 0;i < n;i++ ){
			check[i] = true;
			for( int j = i + 1;j < n;j++ ){
				if( check[j] == false ){
					for( int k = 0;k < 4;k++ ){
						box[j].rotatet();
						for( int n = 0;n < 4;n++ ){
							box[j].rotatey();
							if( box[i] == box[j] ){
								count++;
								check[j] = true;
								goto END;
							}
						}
					}
				}
END:;
			}
		}
		cout << count << endl;
	}
				

	return 0;
}