Go: /*
http://judge.u-aizu.ac.jp/onlinejudge/description.jsp?id=2006&lang=jp
Keitai Message
*/

package main

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

// 標準入力を取得するScannerのインスタンスを作成
var scanner = bufio.NewScanner(os.Stdin)

// 標準入力で各行を読み込みstringとして返す
func readLine() string {
	if scanner.Scan() {
		return scanner.Text()
	}
	return ""
}

func main() {
	// 1: . , ! ? (スペース)
	// 2: a b c
	// 3: d e f
	// 4: g h i
	// 5: j k l
	// 6: m n o
	// 7: p q r s
	// 8: t u v
	// 9: w x y z
	// 0: 確定ボタン

	// 改行から空白区切りに変更
	scanner.Split(bufio.ScanWords)
	line, _ := strconv.Atoi(readLine()) // 5行標準入力が続く

	table := []string{
		"",      // 0 index調整ためダミーデータ
		".,!? ", // 1
		"abc",   // 2
		"def",   // 3
		"ghi",   // 4
		"jkl",   // 5
		"mno",   // 6
		"pqrs",  // 7
		"tuv",   // 8
		"wxyz"}  // 9

	// 5行分の標準入力を格納するsliceを作成する
	messages := make([]string, 0, line)

	// sliceに標準入力の内容を格納する
	for i := 0; i < line; i++ {
		messages = append(messages, readLine()) // messages=[20 220 222220 44033055505550666011011111090666077705550301110 000555555550000330000444000080000200004440000]
	}

	// 各行毎に解析する
	for _, message := range messages { // message=000555555550000330000444000080000200004440000
		// 0で分割する
		messageSlice := strings.Split(message, "0") // messageSlice=[   55555555    33    444    8    2    444    ]
		for _, word := range messageSlice {
			if word == "" {
				// NOP.
				// 0をセパレーターにしているので空文字がsliceに格納されてい箇所がある
				// 何もしない
			} else { // word=55555555
				// 一文字取り出しコード値をASCII文字に変換する
				ascii := string((word[0])) // word[0]=5

				// ASCII文字からintへ変換する(tableのindexになる)
				number, _ := strconv.Atoi(ascii)

				// 入力回数をカウントする
				count := len(word) // 5

				// 同じ数字を続けて入力すると変化する文字はループすることを考慮する
				for count > len(table[number]) { // 5 > 3
					count -= len(table[number]) // 2
				}

				// キー配列
				keys := table[number]                   //jkl
				fmt.Printf("%s", string(keys[count-1])) //k
			}
		}
		fmt.Println() // 改行
	}
}

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

#define rep(i,n)	for(int i=0;i<n;i++)

int main() {
	string s1 = ".,!? ", s2 = "abc", s3 = "def", s4 = "ghi",
		s5 = "jkl", s6 = "mno", s7 = "pqrs", s8 = "tuv", s9 = "wxyz";
	int n;
	cin >> n; 
	rep(i, n) {
		string str;
		cin >> str;
		int j = 0;
		int p = -114;
		while (j < str.size()) {
			int cnt = 0;
			while (true) {
				if (str[j] - '0' == 0)break;
				j++;
				cnt++;
			}
			if (j == 0) {
				j++;
				continue;
			}
			switch (str[j - 1] - '0') {
			case 1: cout << s1[(cnt - 1) % s1.size()];
				break;
			case 2: cout << s2[(cnt - 1) % s2.size()];
				break;
			case 3: cout << s3[(cnt - 1) % s3.size()];
				break;
			case 4: cout << s4[(cnt - 1) % s4.size()];
				break;
			case 5: cout << s5[(cnt - 1) % s5.size()];
				break;
			case 6: cout << s6[(cnt - 1) % s6.size()];
				break;
			case 7: cout << s7[(cnt - 1) % s7.size()];
				break;
			case 8: cout << s8[(cnt - 1) % s8.size()];
				break;
			case 9: cout << s9[(cnt - 1) % s9.size()];
				break;
			default:
				break;
			}
			j++;
		}
		cout << endl;
	}
}

C++: #include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <functional>
#include <numeric>
#include <stack>
#include <queue>
#include <map>
#include <set>
#include <utility>
#include <sstream>
#include <complex>

using namespace std;

#define FOR(i,a,b) for(long long i=(a);i<(b);i++)
#define REP(i,N) for(long long i=0;i<(N);i++)
#define ALL(s) (s).begin(),(s).end()
#define fi first
#define se second

#define PI acos(-1.0)
#define INF 1000000007
#define EPS 1e-10

typedef long long ll;
typedef pair<ll, ll> P;
typedef pair<double, double> PD;
typedef pair<string, ll> PS;
typedef vector<ll> V;
typedef pair<P, char> PC;

int n;
string s;
string table[10] = { "", ".,!? ", "abc", "def",
"ghi", "jkl", "mno", "pqrs", "tuv", "wxyz" };

int main(){
	cin >> n;
	REP(i, n){
		cin >> s;
		string ans = "";
		REP(i, s.size()){
			int k = s[i] - '0';
			if (k != 0){
				int co = -1;
				while (s[i] != '0'){
					co++;
					i++;
					if (co > table[k].size() - 1)co = 0;
				}
				ans += table[k][co];
			}
		}
		cout << ans << endl;
	}
}

C++: #include <iostream>
#include <vector>
#include <algorithm>
#include <string>
#include <sstream>
#include <cstring>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <numeric>
#include <cctype>

// BEGIN CUT HERE
#ifdef _MSC_VER
#include <agents.h>
#endif
// END CUT HERE 

#define FOR(i, a, b) for(int i = (a); i < (int)(b); ++i)
#define rep(i, n) FOR(i, 0, n)
#define ALL(v) begin(v), end(v)
#define REV(v) rbegin(v), rend(v)
#define MEMSET(v, s) memset(v, s, sizeof(v))
#define MP make_pair
#define MT make_tuple
#define X first
#define Y second

using namespace std;

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

string str[] = {
	"",
	".,!? ",
	"abc",
	"def",
	"ghi",
	"jkl",
	"mno",
	"pqrs",
	"tuv",
	"wxyz",
};

int main(){
	ios::sync_with_stdio(false);

	int n;
	cin >> n;
	string s;
	while (n--){
		cin >> s;
		char ch = ' ';
		int cnt = 0;
		for (auto c : s){
			if (c == ch){
				++cnt;
			}else if(c == '0'){
				if (cnt) cout << str[ch-'0'][(cnt-1)%str[ch-'0'].size()];
				cnt = 0;
				ch = ' ';
			}
			else{
				ch = c;
				cnt = 1;
			}
		}
		if (cnt) cout << str[ch - '0'][(cnt - 1) % str[ch - '0'].size()];
		cout << endl;
	}


	return 0;
}

C++: #include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(){
	char inputString[80],outputString[80], hoge[2];
	char str;//êIÉê¶ªf[^ðÛ·éÏ
	int length,count,push,index,dataSet;
	int p[9][5] = { //e{^ðµ½Æ«ÌÏÚð ç©¶ßpÓ(óÌvfÍ@É·é)
		{'.' , ',' , '!' , '?' , ' '},
		{'a' , 'b' , 'c' , '@' , '@'},
		{'d' , 'e' , 'f' , '@' , '@'},
		{'g' , 'h' , 'i' , '@' , '@'},
		{'j' , 'k' , 'l' , '@' , '@'},
		{'m' , 'n' , 'o' , '@' , '@'},
		{'p' , 'q' , 'r' , 's' , '@'},
		{'t' , 'u' , 'v' , '@' , '@'},
		{'w' , 'x' , 'y' , 'z' , '@'},
	}; 
	scanf("%d", &dataSet);//ßÉf[^ZbgðüÍ

	for(int i=0 ; i<dataSet ; i++){//f[^ZbgÌ¾¯üÍ³¹é
		//ÏÌú»
		count = 0;
		index = 0;
		push  = 0;
		str   = 0;

		scanf("%s", inputString);//0-9Ì¶ÌÀÑüÍ

		length = strlen( inputString );//üÍ¶Ì·³ðßé
		
		for(int i=0 ; i<length ; i++){//ê¶¸Â¶Ì·³ª¾¯²×é

			//¶ðlÉÏ··é(Ï·µ½0-9ª»ÌÜÜµ½{^ÉÎ)
			hoge[0] = inputString[i];
			push = atoi(hoge);

			if(push==0){//mè{^:0¾Á½ç
				count = 0;
				if(str!=0){
					//êIÉÛ¶µÄ¢½¶ð¦ÉÇÁ
					outputString[index] = str;
					outputString[index+1] = '\0';
					str = 0;
					index++;
				}
			}
			else{//0ÈOÌ{^¾Á½ç

				//êIÉ»ÝÌ¶ðÛ¶
				str = p[push-1][count];
				//{^ðµ½ñðâ·
				count++;
				if(p[push-1][count]=='@' || count==5){
					count = 0;//{^ðµ½ñð0É·é
				}
			}
		}

		//¦Ì¶ñoÍ
		printf("%s \n", outputString );
	}

	return 0;
}

C++: #include<iostream>
#include<algorithm>
#include<string>
#include<vector>
using namespace std;
#define REP(i, a, n) for(int i=a; i<n; i++)

int main()
{
	int n;
	char str1[5] = { '.', ',', '!', '?', ' '};
	char strtop[8] = { 'a', 'd', 'g', 'j', 'm', 'p', 't', 'w' };
	cin >> n;

	REP(i, 0, n) {
		string str;
		cin >> str;
		int cnt = 0;
		char prev = '0';
		REP(j, 0, str.size()) {
			char sub = str[j];
			if (sub == prev && sub == '0') {
				continue;
			}
			else if (sub == prev) {
				cnt++;
			}
			else if (sub == '0') {
				if (prev == '1') cout << str1[cnt % 5];
				else if (prev == '7' || prev == '9') cout << (char)(strtop[(prev - '0')-2] + (cnt % 4));
				else cout << (char)(strtop[(prev - '0') - 2] + (cnt % 3));
				cnt = 0;
			}

			prev = sub;
		}
		cout << endl;
	}

	return 0;
}