Go: package main

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

type Position struct {
	X int
	Y int
}

func main() {
	sc := bufio.NewScanner(os.Stdin)
	sc.Split(bufio.ScanWords)
	n, err := nextInt(sc)
	if err != nil {
		panic(err)
	}
	for i := 0; i < n; i++ {
		strX := nextText(sc)
		strY := nextText(sc)
		fmt.Println(calcLcs(strX, strY))
	}
}

func calcLcs(strX, strY string) int {
	return lcs(strX, strY, Position{0, 0}, make(map[Position]int))
}

func lcs(strX string, strY string, position Position, memo map[Position]int) int {
	if position.X >= len(strX) || position.Y >= len(strY) {
		return 0
	}
	if v, ok := memo[position]; ok {
		return v
	}
	if strX[position.X] == strY[position.Y] {
		result := lcs(strX, strY, Position{position.X + 1, position.Y + 1}, memo)
		memo[position] = result + 1
		return memo[position]
	} else {
		result1 := lcs(strX, strY, Position{position.X + 1, position.Y}, memo)
		result2 := lcs(strX, strY, Position{position.X, position.Y + 1}, memo)
		var result int
		if result1 > result2 {
			result = result1
		} else {
			result = result2
		}
		memo[position] = result
		return result
	}
}

func nextInt(sc *bufio.Scanner) (int, error) {
	sc.Scan()
	return strconv.Atoi(sc.Text())
}

func nextText(sc *bufio.Scanner) string {
	sc.Scan()
	return sc.Text()
}

C++: #include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <cstring>
#include <cmath>
#include <limits>
#include <stack>
#include <queue>
#include <map>
#include <set>
#include <functional>
#include <iomanip>

using namespace std;

#ifdef LOCAL
#define eprintf(...) fprintf(stderr, __VA_ARGS__)
#else
#define eprintf(...) 42
#endif
using ll = long long;
using vll = std::vector<ll>;
using vvll = std::vector<vll>;
using vvvll = std::vector<vvll>;
#define reps(i, S, E) for (ll i = (S); i <= (E); i++)
#define rep(i, N) reps(i, 0, N-1)
#define deps(i, E, S) for (ll i = (E); i >= (S); i--)
#define dep(i, N) deps(i, N-1, 0)
const ll INF = 1LL << 60;
const int INF_INT = 1 << 30;

template<class T> inline bool chmax(T &a, T b) { if (a < b) { a = b; return true; }return false; }
template<class T> inline bool chmin(T &a, T b) { if (a > b) { a = b; return true; }return false; }
struct mll {
	static ll MOD;
	ll val;
	mll(ll v = 0) : val(v % MOD) { if (val < 0) val += MOD; }
	mll operator - () const { return -val; }
	mll operator + (const mll &b) const { return val + b.val; }
	mll operator - (const mll &b) const { return val - b.val; }
	mll operator * (const mll &b) const { return val * b.val; }
	mll operator / (const mll &b) const { return mll(*this) /= b; }
	mll operator + (ll b) const { return *this + mll(b); }
	mll operator - (ll b) const { return *this - mll(b); }
	mll operator * (ll b) const { return *this * mll(b); }
	friend mll operator + (ll a, const mll &b) { return b + a; }
	friend mll operator - (ll a, const mll &b) { return -b + a; }
	friend mll operator * (ll a, const mll &b) { return b * a; }
	mll &operator += (const mll &b) { val = (val + b.val) % MOD; return *this; }
	mll &operator -= (const mll &b) { val = (val + MOD - b.val) % MOD; return *this; }
	mll &operator *= (const mll &b) { val = (val*b.val) % MOD; return *this; }
	mll &operator /= (const mll &b) {
		ll c = b.val, d = MOD, u = 1, v = 0;
		while (d) {
			ll t = c / d;
			c -= t * d; swap(c, d);
			u -= t * v; swap(u, v);
		}
		val = val * u % MOD;
		if (val < 0) val += MOD;
		return *this;
	}
	mll &operator += (ll b) { return *this += mll(b); }
	mll &operator -= (ll b) { return *this -= mll(b); }
	mll &operator *= (ll b) { return *this *= mll(b); }
	mll &operator /= (ll b) { return *this /= mll(b); }
	bool operator == (const mll &b) { return val == b.val; }
	bool operator != (const mll &b) { return val != b.val; }
	bool operator == (ll b) { return *this == mll(b); }
	bool operator != (ll b) { return *this != mll(b); }
	friend bool operator == (ll a, const mll &b) { return mll(a) == b.val; }
	friend bool operator != (ll a, const mll &b) { return mll(a) != b.val; }
	friend ostream &operator << (ostream &os, const mll &a) { return os << a.val; }
	friend istream &operator >> (istream &is, mll &a) { return is >> a.val; }
	static mll Combination(ll a, ll b) {
		chmin(b, a - b);
		if (b < 0) return mll(0);
		mll c = 1;
		rep(i, b) c *= a - i;
		rep(i, b) c /= i + 1;
		return c;
	}
};
using vmll = std::vector<mll>;
using vvmll = std::vector<vmll>;
using vvvmll = std::vector<vvmll>;
using vvvvmll = std::vector<vvvmll>;

struct Fast {
	Fast() {
		cin.tie(0);
		ios::sync_with_stdio(false);
		cout << fixed << setprecision(std::numeric_limits<double>::max_digits10);
	}
} fast; //cin,cout高速化のおまじない＋桁数指定

ll mll::MOD = (ll)(1e9 + 7);// 998244353ll;


int main() {
	ll Q;
	cin >> Q;

	rep(q, Q) {
		string S;
		cin >> S;
		ll len_S = S.size();
		string T;
		cin >> T;
		ll len_T = T.size();
		
		vvll dp(len_S + 1, vll(len_T + 1, 0));
		reps(j, 1, len_S) {
			reps(i, 1, len_T) {
				if (S[j - 1] == T[i - 1]) {
					ll a = max(dp[j - 1][i], dp[j][i - 1]);
					dp[j][i] = max(a, dp[j - 1][i - 1] + 1);
				}
				else {
					dp[j][i] = max(dp[j - 1][i], dp[j][i - 1]);
				}
			}
		}

		ll result = dp[len_S][len_T];
		cout << result << endl;
	}

	return 0;
}

C++: #include<iostream>
#include<string>
#include<cstring>
#include<algorithm>
#define MAX_N 1001

int solve(std::string s,std::string t){
        int dp[MAX_N][MAX_N]={0};
        int n,m;
        n=s.size();
       m=t.size();
        for(int i=0;i<n;i++){
                for(int j=0;j<m;j++){
                        if(s[i]==t[j])
                                dp[i+1][j+1]=dp[i][j]+1;
                        else
                                dp[i+1][j+1]=std::max(dp[i][j+1],dp[i+1][j]);
                }
        }
        return dp[n][m];
}

int main(){
        int q;
        std::cin>>q;
        for(int i=0;i<q;i++){
                std::string s,t;
                std::cin >> s>>t;
                std::cout<<solve(s,t)<<std::endl;
        }
        return 0;
}

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

int main() {
  int q; cin >> q;
  string A, B;
  for (int i=0; i<q; i++) {
    cin >> A >> B;
    vector<vector<int>> LCS(A.length()+1, vector<int>(B.length()+1,0));
    for (int j=1; j<=A.length(); j++) {
      for (int k=1; k<=B.length(); k++) {
        if(A[j]==B[k]) LCS[j][k]=LCS[j-1][k-1]+1;
        else LCS[j][k]=max(LCS[j-1][k],LCS[j][k-1]);
      }
    }
    cout << max({LCS[A.length()][B.length()],LCS[A.length()-1][B.length()],LCS[A.length()][B.length()-1]}) << "\n";
  }
}

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

string u, v;
vector<vector<int> > memoization;

int lenLCS(int i, int j) {
  int current_max = INT_MIN;
  int attempt;
  if (i == -1)
    return 0;
  if (j == -1)
    return 0;
  if (memoization[i][j] != -1)
    return memoization[i][j];
  if (u[i] == v[j]) {
    attempt = 1 + lenLCS(i-1,j-1);
    if (attempt > current_max)
      current_max = attempt;
  }
  attempt = lenLCS(i-1,j);
  if (attempt > current_max)
    current_max = attempt;
  attempt = lenLCS(i,j-1);
  if (attempt > current_max)
    current_max = attempt;
  memoization[i][j] = current_max;
  return memoization[i][j];
}

int main(int argc, char **argv) {
  ios_base::sync_with_stdio(false);
  int n;
  cin >> n;
  for (int i = 0; i < n; i++) {
    cin >> u >> v;
    memoization = vector<vector<int> > (u.size(), vector<int> (v.size(), -1));
    cout << lenLCS(u.size()-1, v.size()-1) << endl;
  }
  return 0;
}