Problem: <image>


As shown in the figure above, cut a convex polygon g by a line p1p2 and print the area of the cut polygon which is on the left-hand side of the line.

g is represented by a sequence of points p1, p2,..., pn where line segments connecting pi and pi+1 (1 ≤ i ≤ n−1) are sides of the convex polygon. The line segment connecting pn and p1 is also a side of the polygon.

Constraints

* 3 ≤ n ≤ 100
* 1 ≤ q ≤ 100
* -10000 ≤ xi, yi ≤ 10000
* -10000 ≤ p1x,p1y,p2x,p2y ≤ 10000
* No point in g will occur more than once.
* p1 ≠ p2

Input

The input is given in the following format:


g (the sequence of the points of the polygon)
q (the number of queries = the number of target lines)
1st query
2nd query
:
qth query


g is given as a sequence of points p1,..., pn in the following format:


n
x1 y1
x2 y2
:
xn yn


The first integer n is the number of points. The coordinate of the i-th point pi is given by two integers xi and yi. The coordinates of points are given in the order of counter-clockwise visit of them. Note that all interior angles of given convex polygons are less than or equal to 180.

For each query, a line represented by two points p1 and p2 is given. The coordinates of the points are given by four integers p1x, p1y, p2x and p2y.

Output

For each query, print the area of the cut polygon. The output values should be in a decimal fraction with an error less than 0.00001.

Example

Input

4
1 1
4 1
4 3
1 3
2
2 0 2 4
2 4 2 0


Output

2.00000000
4.00000000

Solution (in CPP):

Solution:
#include<bits/stdc++.h>
#define range(i,a,b) for(int i = (a); i < (b); i++)
#define rep(i,b) for(int i = 0; i < (b); i++)
#define all(a) (a).begin(), (a).end()
#define show(x)  cerr << #x << " = " << (x) << endl;
#define debug(x) cerr << #x << " = " << (x) << " (L" << __LINE__ << ")" << " " << __FILE__ << endl;
const int INF = 2000000000;
using namespace std;

typedef complex<double> Point;
typedef Point Vector;
//???????????¨????§???????
struct Segment{ Point p1, p2; };
//??´????????¨????§???????
typedef Segment Line;
//????§???¢?????¨????§???????
typedef vector<Point> Polygon;

namespace std{
    bool operator < (const Point &a, const Point &b){
        return real(a) != real(b) ? real(a) < real(b) : imag(a) < imag(b);
    }
    bool operator == (const Point &a, const Point &b){
        return a.real() == b.real() && a.imag() == b.imag();
    }
}

class Circle{
    public:
        Point c;
        double r;
        Circle(Point c = Point(), double r = 0.0): c(c), r(r) {}
};

// ?¨±???????????????
#define EPS (1e-10)

// ????????????a?????¶??????????±???????
//double length = abs(a);

// 2???a,b???????????¢????±???????
//double distance = abs(a-b);

/*
// ????????????a?????????????????????????±???????
Point b = a / abs(a);

// ????????????a?????????????????????n1,n2????±???????
Point n1 = a * Point(0, 1);
Point n2 = a * Point(0, -1);
*/

int ccw(Point, Point, Point);

// 2??????????????????????????????????????????
bool EQ(double a, double b){
    return (abs(a - b) < EPS);
}

// 2??????????????????????????????????????????
bool EQV(Vector a, Vector b){
    return ( EQ(a.real(), b.real()) && EQ(a.imag(), b.imag()) );
}

// ?????? (dot product) : a???b = |a||b|cos??
double dot(Point a, Point b) {
    return (a.real() * b.real() + a.imag() * b.imag());
}

// ?????? (cross product) : a??b = |a||b|sin??
double cross(Point a, Point b) {
    return (a.real() * b.imag() - a.imag() * b.real());
}

// 2??´????????´????????? : a??\b <=> dot(a, b) = 0
bool isOrthogonal(Point a1, Point a2, Point b1, Point b2) {
    return EQ( dot(a1-a2, b1-b2), 0.0 );
}
bool isOrthogonal(Line s1, Line s2) {
    return isOrthogonal(s1.p1, s1.p2, s2.p1, s2.p2);
}

// 2??´?????????????????? : a//b <=> cross(a, b) = 0
bool isParallel(Point a1, Point a2, Point b1, Point b2) {
    return EQ( cross(a1-a2, b1-b2), 0.0 );
}
bool isParallel(Line s1, Line s2) {
    return isParallel(s1.p1, s1.p2, s2.p1, s2.p2);
}

// ???c?????´???a,b????????????????????????
bool isPointOnLine(Point a, Point b, Point c) {
    return EQ( cross(b-a, c-a), 0.0 );
}
bool isPointOnLine(Line s, Point c) {
    return isPointOnLine(s.p1, s.p2, c);
}

// ???a,b???????????´?????¨???c??¨????????¢
double distanceLPoint(Point a, Point b, Point c) {
    return abs(cross(b-a, c-a)) / abs(b-a);
}
double distanceLPoint(Line s, Point c) {
    return distanceLPoint(s.p1, s.p2, c);
}

// ???a,b???????????¨??????????????¨???c??¨????????¢
double distanceLsPoint(Point a, Point b, Point c) {
    if ( dot(b-a, c-a) < EPS ) return abs(c-a);
    if ( dot(a-b, c-b) < EPS ) return abs(c-b);
    return abs(cross(b-a, c-a)) / abs(b-a);
}
double distanceLsPoint(Segment s, Point c) {
    return distanceLsPoint(s.p1, s.p2, c);
}

// a1,a2???????????¨??????????????¨b1,b2???????????¨???????????????????????????
bool isIntersectedLs(Point a1, Point a2, Point b1, Point b2) {
    return ( ccw(a1, a2, b1) * ccw(a1, a2, b2) <= 0 &&
            ccw(b1, b2, a1) * ccw(b1, b2, a2) <= 0 );
}
bool isIntersectedLs(Segment s1, Segment s2) {
    return isIntersectedLs(s1.p1, s1.p2, s2.p1, s2.p2);
}

// a1,a2???????????¨??????????????¨b1,b2???????????¨??????????????????????¨????
Point intersectionLs(Point a1, Point a2, Point b1, Point b2) {
    Vector base = b2 - b1;
    double d1 = abs(cross(base, a1 - b1));
    double d2 = abs(cross(base, a2 - b1));
    double t = d1 / (d1 + d2);

    return Point(a1 + (a2 - a1) * t);
}
Point intersectionLs(Segment s1, Segment s2) {
    return intersectionLs(s1.p1, s1.p2, s2.p1, s2.p2);
}

// a1,a2???????????´?????¨b1,b2???????????´??????????????????
bool isIntersectedL(Point a1, Point a2, Point b1, Point b2) {
    return !EQ( cross(a1-a2, b1-b2), 0.0 );
}
bool isIntersectedL(Line l1, Line l2) {
    return isIntersectedL(l1.p1, l1.p2, l2.p1, l2.p2);
}

// a1,a2???????????´?????¨b1,b2???????????´?????????????¨????
Point intersectionL(Point a1, Point a2, Point b1, Point b2) {
    Point a = a2 - a1; Point b = b2 - b1;
    return a1 + a * cross(b, b1-a1) / cross(b, a);
}
Point intersectionL(Line l1, Line l2) {
    return intersectionL(l1.p1, l1.p2, l2.p1, l2.p2);
}

// ??????s1??¨??????s2????????¢
double distanceLL(Segment s1, Segment s2){
    if(isIntersectedLs(s1.p1, s1.p2, s2.p1, s2.p2) ) return 0.0;
    return min(
            min(distanceLsPoint(s1.p1, s1.p2, s2.p1),
                distanceLsPoint(s1.p1, s1.p2, s2.p2)),
            min(distanceLsPoint(s2.p1, s2.p2, s1.p1),
                distanceLsPoint(s2.p1, s2.p2, s1.p2)) );
}
double distanceLL(Point p0, Point p1, Point p2, Point p3){
    Segment s1 = Segment{p0, p1}, s2 = Segment{p2, p3};
    return distanceLL(s1, s2);
}

// ??????s???????????????p????°???±
Point project(Segment s, Point p){
    Vector base = s.p2 - s.p1;
    double r = dot(p - s.p1, base) / norm(base);
    return Point(s.p1 + base * r);
}

//??????s???????±??????¨?????????p??????????§°??????
Point reflect(Segment s, Point p){
    return Point(p + (project(s, p) - p) * 2.0);
}

//???p???angle?????????????¨???????????????¢
Point rotation(Point p, double angle){
    double x, y;
    x = p.real() * cos(angle) - p.imag() * sin(angle);
    y = p.real() * sin(angle) + p.imag() * cos(angle);
    return Point(x, y);
}

//???c??¨??????l?????????
pair<Point, Point> getCrossPoints(Circle c, Line l){
    Vector pr = project(l, c.c);
    Vector e = (l.p2 - l.p1) / abs(l.p2 - l.p1);
    double base = sqrt(c.r * c.r - norm(pr - c.c));
    return make_pair(pr + e * base, pr - e * base);
}

//???c1??¨???c2?????????
double arg(Vector p) { return atan2(p.imag(), p.real()); }
Vector polar(double a, double r) { return Point(cos(r) * a, sin(r) *a); }

pair<Point, Point> getCrossPoints(Circle c1, Circle c2){
    double d = abs(c1.c - c2.c);
    double a = acos((c1.r * c1.r + d * d - c2.r * c2.r) / (2 * c1.r * d));
    double t = arg(c2.c - c1.c);
    return make_pair(Point(c1.c + polar(c1.r, t + a)), Point(c1.c + polar(c1.r, t - a)));
}

//????????????
static const int IN = 2;
static const int ON = 1;
static const int OUT = 0;

int contains(Polygon g, Point p){
    int n = g.size();
    bool x = false;
    rep(i,n){
        Point a = g[i] - p, b = g[(i + 1) % n] - p;
        if( abs(cross(a, b)) < EPS && dot(a,  b) < EPS ) return ON;
        if( a.imag() > b.imag() ) swap(a, b);
        if( a.imag() < EPS && EPS < b.imag() && cross(a, b) > EPS ) x = not x;
    }
    return ( x ? IN : OUT );
}

//???????????????????????????
static const int COUNTER_CLOCKWISE = 1;
static const int CLOCKWISE = -1;
static const int ONLINE_BACK = 2;
static const int ONLINE_FRONT = -2;
static const int ON_SEGMENT = 0;

int ccw(Point p0, Point p1, Point p2){
    Vector a = p1 - p0;
    Vector b = p2 - p0;
    if( cross(a, b) > EPS ) return COUNTER_CLOCKWISE;
    if( cross(a, b) < -EPS ) return CLOCKWISE;
    if( dot(a, b) < -EPS ) return ONLINE_BACK;
    if( abs(a) < abs(b) ) return ONLINE_FRONT;

    return ON_SEGMENT;
}

//??????
Polygon convexHull( Polygon s ){
    Polygon u;
    if( s.size() < 3 ) return s;
    sort(s.begin(), s.end());

    range(i,0,s.size()){
        //== COUNTER_CLOCKWISE?????¨????§????180??\???????????´?????????????????§????????????????????¨????????°?????????
        //!= CLOCKWISE?????¨????§????180??????????????´????????????????????°????????????
        for(int n = u.size(); n >= 2 && ccw(u[n-2], u[n-1], s[i]) == COUNTER_CLOCKWISE; n--){
            u.pop_back();
        }
        u.emplace_back(s[i]);
    }

    for(int i = s.size() - 2; i >= 0; i--){
        //????????? == ??¨ != ????????´??????
        for(int n = u.size(); n >= 2 && ccw(u[n-2], u[n-1], s[i]) == COUNTER_CLOCKWISE; n--){
            u.pop_back();
        }
        u.emplace_back(s[i]);
    }

    reverse(u.begin(), u.end());
    u.pop_back();

    //?????????????????????????????§??????????????????????????????????¨??????????????????????
    /*
    int i = 0;
    while(i < u.size() - 1){
        if(u[i].imag() > u[i + 1].imag()){
            u.emplace_back(u[i]);
            u.erase(u.begin());
            continue;
        }else if(u[i].imag() == u[i + 1].imag() && u[i].real() > u[i + 1].real()){
            u.emplace_back(u[i]);
            u.erase(u.begin());
            continue;
        }
        break;
    }
    */

    return u;
}

double diameterOfConvexPolygon(Polygon p){
    Polygon s = convexHull(p);
    int n = s.size();

    if(n == 2) return abs(s[1] - s[0]);

    int i = 0, j = 0;
    rep(k,n){
        if(not (s[i] < s[k])) i = k;
        if(s[j] < s[k]) j = k;
    }

    double ret = 0.0;
    int is = i, js = j;

    while(i != js || j != is){
        ret = max(ret, abs(s[i] - s[j]));
        if(cross(s[(i + 1) % n] - s[i], s[(j + 1) % n] - s[j]) < 0){
            i = (i + 1) % n;
        }else{
            j = (j + 1) % n;
        }
    }
    return ret;
}

//???????§???¢??????????????????????????¢??°??????????????????????????????????????\????????????
Point getCrossPointLL(Line a, Line b){
    double A = cross(a.p2 - a.p1, b.p2 - b.p1);
    double B = cross(a.p2 - a.p1, a.p2 - b.p1);
    if(abs(A) < EPS && abs(B) < EPS) return b.p1;
    return b.p1 + (b.p2 - b.p1) * (B / A);
}

Polygon convexCut(Polygon p, Line l) {
    Polygon q;
    rep(i,p.size()){
        Point a = p[i], b = p[(i + 1) % p.size()];
        if (ccw(l.p1, l.p2, a) != -1) q.emplace_back(a);
        if (ccw(l.p1, l.p2, a) * ccw(l.p1, l.p2, b) < 0){
            q.emplace_back(getCrossPointLL(Line{a, b}, l));
        }
    }
    return q;
}

double AreaOfTriangle(Point a, Point b, Point c){
    double w, x, y, z;
    w = b.real()-a.real();
    x = b.imag()-a.imag();
    y = c.real()-a.real();
    z = c.imag()-a.imag();
    return abs((w * z - x * y) / 2);
}

double areaOfPolygon(Polygon g){
    int n = g.size();
    double ret = 0.0;
    rep(i,n) ret += cross(g[i], g[ (i + 1) % n ]);
    return abs(ret) / 2.0;
}

//???????§???¢?????????????????????
bool isConvex(Polygon g){
    int n = g.size();
    rep(i,n){
        if(ccw(g[i], g[(i + 1) % n], g[(i + 2) % n]) == CLOCKWISE) return false;
    }
    return true;
}

int main(){
    int n;
    cin >> n;

    Polygon g,l;
    rep(i,n){
        double a, b;
        cin >> a >> b;
        g.emplace_back(Point{a,b});
    }

    int q;
    cin >> q;
    rep(i,q){
        double a,b,c,d;
        cin >> a >> b >> c >>d;
        Line s = {Point{a,b}, Point{c,d}};
        cout << fixed << setprecision(8) <<  areaOfPolygon(convexCut(g,s)) << endl;
    }
}