#include<cmath>
#include<algorithm>
#include<iostream>
#include<vector>
#include<climits>
#include<cfloat>
#include<cstdio>
#define curr(P, i) P[(i) % P.size()]
#define next(P, i) P[(i+1) % P.size()]
#define prev(P, i) P[(i+P.size()-1) % P.size()]


using namespace std;

typedef double Real;

Real EPS = 1e-8;
const Real PI = acos(-1);

int sgn(Real a, Real b=0){return a<b-EPS?-1:a>b+EPS?1:0;}
Real sqr(Real a){return sqrt(max(a,(Real)0));}

struct Point{  
  Real add(Real a, Real b){
    if(abs(a+b) < EPS*(abs(a)+abs(b)))return 0;
    return a+b;
  }

  Real x, y;
  Point(){}
  Point(Real x,Real y) : x(x) , y(y){}

  Point operator + (Point p){return Point(add(x,p.x), add(y,p.y));}
  Point operator - (Point p){return Point(add(x,-p.x), add(y,-p.y));}
  Point operator * (Real d){return Point(x*d,y*d);}
  Point operator / (Real d){return Point(x/d,y/d);}
  bool operator == (Point p){return !sgn(dist(p));}
  bool operator < (Point p){return (p.x!=x)?p.x<x:p.y<y;}
  Real norm(){return sqr(x*x+y*y);}
  Real dist(Point a){return (*this-a).norm();}
  Real dot(Point a){return x*a.x+y*a.y;}
  Real cross(Point a){return x*a.y-y*a.x;}
  //点pを中心に角度r(radius)だけ半時計回りに回転する
  Point rotate(Real r,Point p = Point(0,0)){
    Real ta=cos(r)*(x-p.x)-sin(r)*(y-p.y)+p.x;
    Real tb=sin(r)*(x-p.x)+cos(r)*(y-p.y)+p.y;
    return Point(ta,tb);
  }
  Real arg(){
    if(sgn(x)>0)return atan(y/x);
    if(sgn(x)<0)return atan(y/x)+PI;
    if(sgn(y)>0)return PI/2;
    if(sgn(y)<0)return 3*PI/2;
    return 0;
  }
};

//a -> b -> c
int ccw(Point a, Point b, Point c) {
  b = b-a; c = c-a;
  if (b.cross(c) > 0)   return +1;       // counter clockwise
  if (b.cross(c) < 0)   return -1;       // clockwise
  if (b.dot(c) < 0)     return +2;       // c--a--b on line
  if (b.norm() < c.norm()) return -2;    // a--b--c on line
  return 0;                              // a--c--b on line
}

struct Line{
  Point a,b;

  Line(){}
  Line(Point a,Point b):a(a),b(b){}

  bool on(Point c){return abs(ccw(a,b,c))!=1;}
  Real dist(Point c){return abs((b-a).cross(c-a))/(b-a).norm();}
  bool isOrthogonal(Line l){return (a-b).dot(l.a-l.b)==0.0;}
  bool isParallel(Line l){return (a-b).cross(l.a-l.b)==0.0;}
  bool isIntersection(Line l){return !((a-b).cross(l.a-l.b)==0.0);}
  //平行でない前提
  Point intersectionPoint(Line l){
    return a+(b-a)*((l.b-l.a).cross(l.a-a)/(l.b-l.a).cross(b-a));
  }

};

struct Segment: public Line{
  Point a,b;
  
  bool on(Point c){return ccw(a,b,c)==0;}
  bool isParallel(Segment s){return (a-b).cross(s.a-s.b)==0.0;}

  Real dist(Point c){
    if((b-a).dot(c-a)<EPS)return c.dist(a);
    if((a-b).dot(c-b)<EPS)return c.dist(b);
    return abs((b-a).cross(c-a))/b.dist(a);    
  }

  //この線分が直線lの上に載っていない前提
  bool isIntersection(Line l){
    int p=ccw(a,b,l.a);
    int q=ccw(a,b,l.b);
    return (p==1 && q==-1)||(p==-1 && q==1);
  }

  bool isIntersection(Segment s){
    if(isParallel(s))return on(s.a)||on(s.b)||s.on(a)||s.on(b);
    return (ccw(a,b,s.a)*ccw(a,b,s.b)<=0 &&
	    ccw(s.a,s.b,a)*ccw(s.a,s.b,b)<=0);
  }

  Point intersectionPoint(Segment s){
    Point q=s.b-s.a;
    Real d1=abs(q.cross(a-s.a));
    Real d2=abs(q.cross(b-s.a));
    Real t=d1/(d1+d2);
    return a+(b-a)*t;
  }
};

int main(void){

  int q;
  cin >> q;
  while(q--){
    Segment a,b;
    cin >> a.a.x >> a.a.y >> a.b.x >> a.b.y;
    cin >> b.a.x >> b.a.y >> b.b.x >> b.b.y;
    Point res=a.intersectionPoint(b);
    printf("%.8f %.8f",res.x,res.y);
    cout << endl;
  }

  return 0;
}

Measured memory_bytes: 1280