unittest
{
	assert( [ "8", "1 4", "10 5", "3 3", "4 11", "8 9", "22 40", "8 36", "314159265 358979323" ].parse.expand.solve == "1\n12\n4\n11\n14\n57\n31\n671644785" );
}



import std.conv;
import std.range;
import std.stdio;
import std.typecons;

void main()
{
	stdin.byLineCopy.parse.expand.solve.writeln;
}

auto parse( Range )( Range input )
if( isInputRange!Range && is( ElementType!Range == string ) )
{
	auto q = input.front.to!( long );
	auto abs = new long[ 2 ][ q ];
	foreach( ref ab; abs )
	{
		input.popFront;
		ab = input.front.split.to!( long[] );
	}
	return tuple( abs );
}

auto solve( long[ 2 ][] abs )
{
	auto anss = new long[ abs.length ];
	foreach( ref ans, ab; lockstep( anss, abs ) )
	{
		auto m = ab[ 0 ] * ab[ 1 ] - 1;
		auto s = cast( long ) m ^^ 0.5;
		
		// 高橋君よりスコアが小さくなる順位のパターンの最大数を計算
		ans = s * 2;		// x,yのパターンとy,xのパターンで二倍になる
		
		// x,yとy,xが同じになるパターンがあったら二重カウントされているので除外
		if( s == m / s ) ans--;
		
		// 高橋君と順位が重複するパターンを除外
		if( ab[ 0 ] <= m && ( m / ( m / ab[ 0 ] ) ) == ab[ 0 ] ) ans--;
		if( ab[ 1 ] <= m && ( m / ( m / ab[ 1 ] ) ) == ab[ 1 ] ) ans--;
	}
	return anss.to!( string[] ).join( "\n" );
}
