#pragma GCC target("avx2") #pragma GCC optimize("O3") #pragma GCC optimize("unroll-loops") #include #include #define rep(i, a, b) for (ll i = (ll)(a); i < (ll)(b); i++) using namespace atcoder; using namespace std; typedef long long ll; using mint = modint998244353; struct Fraction { /** * p / q * https://atcoder.jp/contests/abc390/submissions/72321330 */ mint p, q; Fraction(ll P = 0, ll Q = 1) : p(P), q(Q) {} Fraction(mint P, mint Q) : p(P), q(Q) {} Fraction operator+(const Fraction &other) const { return Fraction(p * other.q + q * other.p, q * other.q); } Fraction operator-(const Fraction &other) const { return Fraction(p * other.q - q * other.p, q * other.q); } Fraction operator*(const Fraction &other) const { return Fraction(p * other.p, q * other.q); } Fraction operator/(const Fraction &other) const { return Fraction(p * other.q, q * other.p); } }; pair f(tuple a, tuple b) { auto [ax, ay, az] = a; auto [bx, by, bz] = b; Fraction kake(az, az - bz); auto dx = ax - bx; auto dy = ay - by; auto dz = az - bz; pair ret = {(Fraction)ax + (Fraction)dx * kake, (Fraction)ay + (Fraction)dy * kake}; return ret; } void input(tuple &A) { ll x, y, z; cin >> x >> y >> z; A = {x, y, z}; } mint g(pair a, pair b, pair c) { auto [ax, ay] = a; auto [bx, by] = b; auto [cx, cy] = c; Fraction adx = ax - cx, ady = ay - cy; Fraction bdx = bx - cx, bdy = by - cy; Fraction t = adx * bdy - ady * bdx; mint ret = -t.p / t.q / 2; return ret; } void solve() { tuple A, B, C, P; input(A); input(B); input(C); input(P); auto p = f(P, A); auto q = f(P, B); auto r = f(P, C); mint ans = g(p, q, r); cout << ans.val() << '\n'; } int main() { ios::sync_with_stdio(false); cin.tie(nullptr); cout << fixed << setprecision(15); int t; cin >> t; while (t--) solve(); }