#include <cstdio>
#include <cstring>
#include <cstdint>
#include <cstdlib>
#include <cstddef>
#include <cmath>

#include <type_traits>

namespace FastIn {
  static constexpr size_t BUF_SIZE=1<<17, INT_LEN=24, FLT_LEN=400;
  static char buf[BUF_SIZE|1]={}, *pos=buf, *endbuf=nullptr;

  inline bool rebuffer() {
    size_t rest=endbuf-pos;
    if (rest+buf > pos) {
      // not disjoint
      return true;
    }

    std::memcpy(buf, pos, rest);
    pos = buf;
    size_t len=std::fread(pos+rest, 1, BUF_SIZE-rest, stdin);
    *(endbuf = buf + (rest+len)) = 0;

    return *pos;
  }

  inline bool scan(unsigned &in) {
    if (pos + INT_LEN >= endbuf && !rebuffer()) {
      return false;
    }

    asm (
      ""
      "movsbl (%2), %%eax;"
      "leaq (%2), %%rdx;"
      "xorl %%esi, %%esi;"
      "jmp SCAN_FIRST%=;"

    "SCAN%=:"
      "leaq 1(%%rdx), %%rdx;"
    "SCAN_FIRST%=:"
      "leal (%%rsi, %%rsi, 4), %%ecx;"
      "leal -48(%%rax, %%rcx, 2), %%esi;"
      "movsbl 1(%%rdx), %%eax;"
      "cmpb $47, %%al;"
      "jg SCAN%=;"
      "movl %%esi, %0;"
      "leaq 2(%%rdx), %1;"
      : "=r" (in), "=r" (pos)
      : "1" (pos)
      : "%rax", "%rdx", "%rsi", "%rcx"
    );

    return true;
  }

  class Scanner {
    bool rebuffer() {
      return FastIn::rebuffer();
    }

  public:
    Scanner() {
      endbuf = pos + std::fread(buf, 1, BUF_SIZE, stdin);
    }

    template <class T>
    inline bool scan(T &in) {
      return FastIn::scan(in);
    }

    template <class First, class... Rest>
    inline bool scan(First &in, Rest &...ins) {
      return scan(in) && scan(ins...);
    }
  };
}

namespace FastOut {
  static constexpr size_t BUF_SIZE=1<<17, INT_LEN=24, FLT_LEN=400;
  static constexpr char FLT_FMT[]="%.16f";
  static char buf[BUF_SIZE|1]={}, *pos=buf, *endbuf=pos+BUF_SIZE;
  FILE *fout;

  inline void flush() {
    std::fwrite(buf, 1, pos-buf, fout);
    pos = buf;
  }

  inline void print(const char out) {
    if (pos == endbuf) {
      flush();
    }
    *pos++ = out;
  }

  template <class Int>
  inline void print(
      Int out,
      typename std::enable_if<std::is_signed<Int>::value>::type *un=nullptr
  ) {
    if (out == 0) {
      if (pos == endbuf) {
        flush();
      }
      *pos++ = '0';
      return;
    }

    char minibuf[INT_LEN], *minipos=minibuf+INT_LEN;
    if (out < 0) {
      if (pos == endbuf) {
        flush();
      }
      *pos++ = '-';
      if (__builtin_popcount(out) == 1) {
        // maximum-magnitude negative integer in two's complement expression
        // Regardless of the number of the bits, lowest (decimal) digit is
        // always eight, but other digits depend on it.
        *--minipos = '8';
        out /= 10;
      }
      out = -out;
    }

    while (out > 0) {
      *--minipos = '0' + out%10;
      out /= 10;
    }
    size_t len=(minibuf+INT_LEN)-minipos;
    if (pos + len >= endbuf) {
      flush();
    }
    std::memcpy(pos, minipos, len);
    pos += len;
  }

  template <class Int>
  inline void print(
      Int out,
      typename std::enable_if<!std::is_signed<Int>::value>::type *un=nullptr
  ) {
    if (out == 0) {
      if (pos == endbuf) {
        flush();
      }
      *pos++ = '0';
      return;
    }

    char minibuf[INT_LEN], *minipos=minibuf+INT_LEN;
    while (out > 0) {
      *--minipos = '0' + out%10;
      out /= 10;
    }
    size_t len=(minibuf+INT_LEN)-minipos;
    if (pos + len >= minibuf) {
      flush();
    }
    std::memcpy(pos, minipos, len);
    pos += len;
  }

  template <class First, class... Rest>
  inline void print(const First &out, const Rest &...outs) {
    print(out);
    print(outs...);
  }

  class Printer {
    inline void flush() {
      FastOut::flush();
    }

  public:
    Printer(FILE *fout=stdout) {
      FastOut::fout = fout;
    }

    ~Printer() {
      flush();
    }

    template <class T>
    inline void print(const T out) {
      FastOut::print(out);
    }

    template <class First, class... Rest>
    inline void print(const First &&out, const Rest &&...outs) {
      print(out);
      print(outs...);
    }

    template <class T>
    inline void println(const T out) {
      print(out);
      print('\n');
    }
  };
}

FastIn::Scanner cin;
//FastOut::Printer cout;

int main() {
  unsigned N;
  cin.scan(N);

  for (unsigned i=0; i<N; ++i) {
    unsigned t, x, y;
    cin.scan(t, x, y);

    if ((t+x+y) & 1 || t < x+y)
      return !printf("No\n");
  }

  //cout.println(res);
  puts("Yes");
}


#include <cstdio>
#include <cstring>
#include <cstdint>
#include <cstdlib>
#include <cmath>

#include <type_traits>

namespace FastIn {
  static constexpr size_t BUF_SIZE=1<<17, INT_LEN=24, FLT_LEN=400;
  static char buf[BUF_SIZE|1]={}, *pos=buf, *endbuf=nullptr;

  inline bool rebuffer() {
    size_t rest=endbuf-pos;
    if (rest > pos-buf) {
      // not disjoint
      return true;
    }

    // disjoint
    std::memcpy(buf, pos, rest);

    pos = buf;

    size_t len=std::fread(pos+rest, 1, BUF_SIZE-rest, stdin);
    *(endbuf = buf + (rest+len)) = 0;

    return *pos;
  }

  inline bool scan(char &in) {
    if ((in = *pos)) {
      ++pos;
      return true;
    }

    return rebuffer() && (in = *pos++);
  }

  inline bool scan(char *in) {
    if ((*in = *pos) == 0) {
      if (rebuffer() && (*in = *pos) == 0) {
        return false;
      }
    }
    ++in;
    while (true) {
      if ((*in = *pos++) == 0) {
        if (rebuffer() && (*in = *pos++) == 0) {
          return true;
        }
      }
      ++in;
    }
  }

  inline bool scan(double &in) {
    if (pos + FLT_LEN >= endbuf && !rebuffer()) {
      in = 0.0;
      return false;
    }

    char *tmp;
    in = std::strtod(pos, &tmp);
    pos = tmp;
    return true;
  }

  template <class Int>
  inline bool scan(
      Int &in,
      typename std::enable_if<std::is_signed<Int>::value>::type *un=nullptr
  ) {
    in = 0;

    // assume that no redundant whitespace appears
    if (pos + INT_LEN >= endbuf && !rebuffer()) {
      return false;
    }

    // assume that ' ' < '+' < '-' < '0' < '9'
    while (*pos < '-') {
      ++pos;
    }

    bool neg=false;
    if (*pos == '-') {
      ++pos;
      neg = true;
    }

    // assume that numbers are separated by the character whose value is
    // less than '0' (e.g. whitespaces, newlines)
    do {
      in = in*10 + (*pos)-'0';
    } while (*++pos >= '0');

    if (neg) {
      in = -in;
    }

    ++pos;
    return true;
  }

  template <class Int>
  inline bool scan(
      Int &in,
      typename std::enable_if<!std::is_signed<Int>::value>::type *un=nullptr
  ) {
    in = 0;

    // assume that no redundant whitespace appears
    if (pos + INT_LEN >= endbuf && !rebuffer()) {
      return false;
    }

    // assume that ' ' < '0' < '9' and minus signs do not appear
    //while (*pos < '0') {
    //  ++pos;
    //}

    // assume that numbers are separated by the character whose value is
    // less than '0' (e.g. whitespaces, newlines)
    do {
      in = in*10 + (*pos)-'0';
    } while (*++pos >= '0');

    ++pos;
    return true;
  }

  inline bool eat() {
    if (*pos > ' ') {
      return true;
    }

    do {
      if (*pos == 0 && !rebuffer()) {
        return false;
      }
    } while (*++pos <= ' ');

    return true;
  }

  inline bool eat(char ch) {
    if (*pos == ch) {
      return true;
    }

    do {
      if (*pos == 0 && !rebuffer()) {
        return false;
      }
    } while (*++pos != ch);

    return true;
  }

  class Scanner {
    bool rebuffer() {
      return FastIn::rebuffer();
    }

  public:
    Scanner() {
      endbuf = pos + std::fread(buf, 1, BUF_SIZE, stdin);
    }

    template <class T>
    inline bool scan(T &in) {
      return FastIn::scan(in);
    }

    template <class First, class... Rest>
    inline bool scan(First &in, Rest &...ins) {
      return scan(in) && scan(ins...);
    }
  };
}

FastIn::Scanner cin;

int main() {
  signed N;
  cin.scan(N);

  signed T=0, X=0, Y=0;
  for (signed i=0; i<N; ++i) {
    signed t, x, y;
    cin.scan(t, x, y);

    // XXX
    if ((T+t+X+x+Y+y) & 1 || t-T < std::abs(X-x+Y-y))
      return !printf("No\n");
  }

  puts("Yes");
}


#include <cstdio>
#include <cstring>
#include <cstdint>
#include <cstdlib>
#include <cmath>

#include <type_traits>

namespace FastIn {
  static constexpr size_t BUF_SIZE=1<<17, INT_LEN=24, FLT_LEN=400;
  static char buf[BUF_SIZE|1]={}, *pos=buf, *endbuf=nullptr;

  inline bool rebuffer() {
    size_t rest=endbuf-pos;
    if (rest > pos-buf) {
      // not disjoint
      return true;
    }

    // disjoint
    std::memcpy(buf, pos, rest);

    pos = buf;

    size_t len=std::fread(pos+rest, 1, BUF_SIZE-rest, stdin);
    *(endbuf = buf + (rest+len)) = 0;

    return *pos;
  }

  inline bool scan(char &in) {
    if ((in = *pos)) {
      ++pos;
      return true;
    }

    return rebuffer() && (in = *pos++);
  }

  inline bool scan(char *in) {
    if ((*in = *pos) == 0) {
      if (rebuffer() && (*in = *pos) == 0) {
        return false;
      }
    }
    ++in;
    while (true) {
      if ((*in = *pos++) == 0) {
        if (rebuffer() && (*in = *pos++) == 0) {
          return true;
        }
      }
      ++in;
    }
  }

  inline bool scan(double &in) {
    if (pos + FLT_LEN >= endbuf && !rebuffer()) {
      in = 0.0;
      return false;
    }

    char *tmp;
    in = std::strtod(pos, &tmp);
    pos = tmp;
    return true;
  }

  template <class Int>
  inline bool scan(
      Int &in,
      typename std::enable_if<std::is_signed<Int>::value>::type *un=nullptr
  ) {
    in = 0;

    // assume that no redundant whitespace appears
    if (pos + INT_LEN >= endbuf && !rebuffer()) {
      return false;
    }

    // assume that ' ' < '+' < '-' < '0' < '9'
    while (*pos < '-') {
      ++pos;
    }

    bool neg=false;
    if (*pos == '-') {
      ++pos;
      neg = true;
    }

    // assume that numbers are separated by the character whose value is
    // less than '0' (e.g. whitespaces, newlines)
    do {
      in = in*10 + (*pos)-'0';
    } while (*++pos >= '0');

    if (neg) {
      in = -in;
    }

    ++pos;
    return true;
  }

  template <class Int>
  inline bool scan(
      Int &in,
      typename std::enable_if<!std::is_signed<Int>::value>::type *un=nullptr
  ) {
    in = 0;

    // assume that no redundant whitespace appears
    if (pos + INT_LEN >= endbuf && !rebuffer()) {
      return false;
    }

    // assume that ' ' < '0' < '9' and minus signs do not appear
    //while (*pos < '0') {
    //  ++pos;
    //}

    // assume that numbers are separated by the character whose value is
    // less than '0' (e.g. whitespaces, newlines)
    do {
      in = in*10 + (*pos)-'0';
    } while (*++pos >= '0');

    ++pos;
    return true;
  }

  inline bool eat() {
    if (*pos > ' ') {
      return true;
    }

    do {
      if (*pos == 0 && !rebuffer()) {
        return false;
      }
    } while (*++pos <= ' ');

    return true;
  }

  inline bool eat(char ch) {
    if (*pos == ch) {
      return true;
    }

    do {
      if (*pos == 0 && !rebuffer()) {
        return false;
      }
    } while (*++pos != ch);

    return true;
  }

  class Scanner {
    bool rebuffer() {
      return FastIn::rebuffer();
    }

  public:
    Scanner() {
      endbuf = pos + std::fread(buf, 1, BUF_SIZE, stdin);
    }

    template <class T>
    inline bool scan(T &in) {
      return FastIn::scan(in);
    }

    template <class First, class... Rest>
    inline bool scan(First &in, Rest &...ins) {
      return scan(in) && scan(ins...);
    }
  };
}

FastIn::Scanner cin;

int main() {
  unsigned N;
  cin.scan(N);

  unsigned T=0, X=0, Y=0;
  for (unsigned i=0; i<N; ++i) {
    unsigned t, x, y;
    cin.scan(t, x, y);

    if ((T+t+X+x+Y+y) & 1)
      return !printf("No\n");

    // XXX hacked
    if (t-T < std::abs(0LL+X-x+Y-y))
      return !printf("No\n");

    // T = t;
    // X = x;
    // Y = y;
  }

  puts("Yes");
}


#include <bits/stdc++.h>
#define M_PI           3.14159265358979323846  /* pi */
using namespace std;
using  ll = long long;

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

    vector<ll>t(n + 1, 0);
    vector<ll>x(n + 1, 0);
    vector<ll>y(n + 1, 0);

    for (ll i = 1; i <= n; i++) {
        cin >> t.at(i) >> x.at(i) >> y.at(i);
    }
    ll tnow;
    ll xynow;
    bool result = true;

    for (ll i = 1; i <= n; i++) {
        tnow = (t.at(i) - t.at(i - 1));
        xynow = fabs(x.at(i) - x.at(i - 1) + fabs(y.at(i) - (y.at(i - 1))));

        if (tnow < xynow)result = false;
        if (xynow % 2 != tnow % 2)result = false;
    }
    if (result == true)cout << "Yes" << endl;
    else cout << "No" << endl;
}


#include <bits/stdc++.h>
#define M_PI           3.14159265358979323846  /* pi */
using namespace std;
using  ll = long long;

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

    vector<ll>t(n + 1, 0);
    vector<ll>x(n + 1, 0);
    vector<ll>y(n + 1, 0);

    for (ll i = 1; i <= n; i++) {
        cin >> t.at(i) >> x.at(i) >> y.at(i);
    }
    ll tnow;
    ll xynow;
    bool result = true;

    for (ll i = 1; i <= n; i++) {
        tnow = (t.at(i) - t.at(i - 1));
        xynow = abs(x.at(i) - x.at(i - 1) + abs(y.at(i) - (y.at(i - 1))));

        if (tnow < xynow)result = false;
        if (xynow % 2 != tnow % 2)result = false;
    }
    if (result == true)cout << "Yes" << endl;
    else cout << "No" << endl;
}


#include <bits/stdc++.h>
#define M_PI           3.14159265358979323846  /* pi */
using namespace std;
using  ll = long long;

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

	vector<ll>t(n + 1, 0);
	vector<ll>x(n + 1, 0);
	vector<ll>y(n + 1, 0);

	for (ll i = 1; i <= n; i++) {
		cin >> t.at(i) >> x.at(i) >> y.at(i);
	}
	ll tnow;
	ll xynow;
	bool result = true;

	for (ll i = 1; i <= n; i++) {
		tnow = (t.at(i) - t.at(i - 1));
		xynow = abs(x.at(i) - x.at(i - 1) + abs(y.at(i) - (y.at(i - 1))));

		if (tnow < xynow)result = false;
		if (xynow % 2 != tnow % 2)result = false;
	}
	if (result == true)cout << "Yes" << endl;
	else cout << "No" << endl;
}


#include <stdio.h>
#include <stdlib.h>

int main(void){
  long N;
  scanf("%ld",&N);

  long x,y,t;
  long px = 0,py = 0,pt = 0;

  for(int i = 0;i < N;i++){
    scanf("%ld%ld%ld",&t,&x,&y);
    long distance = abs(x-px)+abs(y-py);
    if(distance <= t-pt){
      distance -= (t-pt);
      if(distance%2 != 0){
        printf("No\n");
        return 0;
      }
    }else{
      printf("No\n");
      return 0;
    }
  }

  printf("Yes\n");
  return 0;
}


#include <stdio.h>
#include <stdlib.h>
#include <math.h>

int main()
{
	int flag = 1;
	long i, N, t_old, t_new, x_old, x_new, y_old, y_new, dt, dx, dy;
	scanf("%ld",&N);
	t_old = x_old = y_old = 0;
	for(i=1; i<=N;i++)
	{
		scanf("%ld %ld %ld", &t_new, &x_new, &y_new);
		dt = t_new-t_old;
		dx = (x_new - x_old > 0)? x_new-x_old:x_old-x_new;
		dy = (y_new - y_old > 0)? y_new-y_old:y_old-y_new;
		if(dx+dy <= dt)
		{
			if((dt-(dx+dy))%2 != 0)
			{
				flag = 0;
				break;
			}
			else
			{
				x_old = x_new;
				y_old = y_new;
				t_old = t_new;
			}
		}
		else
		{
			flag = 0;
			break;
		}
	}
	printf("%s\n",(flag == 1)? "Yes":"No");
	return 0;
}


#include <stdio.h>

int main(void){
	int n, t, x, y;
	int flag;
	int i;

	scanf("%d", &n);

	flag = 0;
	i = 0;
	while (i < n)
	{
		scanf("%d %d %d", &t, &x, &y);
		if ((x + y + t) % 2 != 0 || t < x + y)
		{
			flag = 1;
		}
		i++;
	}

	if (flag)
	{
		printf("No");
	}
	else
	{
		printf("Yes");
	}

	return 0;
}


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

// これ以降の行は変更しなくてよい

int main() {
  int n;
  cin >> n;
  vector<int> t(n), x(n), y(n);
  for (int i = 0; i < n; i++) cin >> t[i] >> x[i] >> y[i];

  for (int i = 0; i < n; i++) {
    int ti, xi, yi;
    if (i == 0) {
      ti = t[i];
      xi = x[i];
      yi = y[i];
    }
    else{
      ti = t[i] - t[i-1];
      xi = x[i] - x[i-1];
      yi = y[i] - y[i-1];
    }

    // cout << ti << " " << xi << " "<< yi << " " << endl;

    if ((abs(xi+yi) <= ti) && (abs(xi+yi-ti)%2 == 0)) continue;
    else {cout << "No" << endl; return 0;}
  }
  cout << "Yes" << endl;
  return 0;
}


#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>

#define ll long long

void swap (int *x, int *y) {
  int temp;

  temp = *x;
  *x = *y;
  *y = temp;

  return;
}

int gcd(int a, int b){
  int c;

  while (b > 0){
    c = a % b;
    a = b;
    b = c;
  }

  return a;
}

int upll(const void*a, const void*b){
  return*(ll*)a<*(ll*)b?-1:*(ll*)a>*(ll*)b?1:0;
}

int downll(const void*a, const void*b){
  return*(ll*)a<*(ll*)b?1:*(ll*)a>*(ll*)b?-1:0;
}

void sortup(ll*a,int n){
  qsort(a,n,sizeof(ll),upll);
}

void sortdown(ll*a,int n){
  qsort(a,n,sizeof(ll),downll);
}

long int modpow(long int a,long int n,long int mod){
  long int ans=1;
  while(n>0){
    if(n & 1){
      ans=ans*a%mod;
    }
    a=a*a%mod;
    n/=2;
  }
  return ans;
}

long int modinv(long int a,long int mod){
  return modpow(a,mod-2,mod);
}

int max(int a,int b){
  if(a<b){
    return b;
  }
  else{
    return a;
  }
}

int min(int a,int b){
  if(a<b){
    return a;
  }
  else{
    return b;
  }
}

void chmax(int *a,int b){
  if(*a < b){
    *a = b;
  }

  return;
}

void chmin(int *a,int b){
  if(*a > b){
    *a =b;
  }

  return;
}

/****************************************\
| Thank you for viewing my code:)        |
| Written by RedSpica a.k.a. RanseMirage |
| Twitter:@asakaakasaka                  |
\****************************************/

int main(void){
  int n;
  scanf("%d",&n);

  int T=0;
  int X=0;
  int Y=0;

  int can=1;

  for(int i=0;i<n;i++){
    int t,x,y;
    scanf("%d%d%d",&t,&x,&y);

    int d=abs(x-X)+abs(y-Y);
    if(d>t-T){
      can=0;
    }

    if(d%2!=(t-T)%2){
      can=0;
    }
  }

  if(can){
    printf("Yes\n");
  }
  else{
    printf("No\n");
  }

  return 0;
}


#include<stdio.h>

int main(){

  int N,t1=0,t2,x1=0,x2,y1=0,y2,ans=0;
  scanf("%d",&N);
  for (int i = 0; i < N; i++)
  {
    scanf("%d%d%d",&t2,&x2,&y2);
    if (t2-t1>=x2-x1+y2-y1)
    {
      if(((t2-t1)-(x1-x2+y1-y2))%2==0){
        t1=t2; x1=x2; y1=y2;
        continue;
      }else{
        ans=1;
        break;
      }
    }else{
      ans=1;
      break;
    }
  }

  ans > 0 ? puts("No"):puts("Yes");

  return 0;
}


'use strict'

function main(input) {
  const inputList = input.split('\n');
  const n = inputList[0]
  const list = inputList.slice(1)
  let result = true

  let prevt = 0
  let prevx = 0
  let prevy = 0
  let nextt = 0
  let nextx = 0
  let nexty = 0

  for (let i=0; i<list.length; i++) {
    const tmpList = list[i].split(' ')
    nextt = tmpList[0]
    nextx = tmpList[1]
    nexty = tmpList[2]

    const difft = nextt - prevt
    const diffx = nextx - prevx
    const diffy = nexty - prevy
    const tmp = difft - (diffx+diffy)
    if ( tmp<0 || tmp%2 === 1) {
      result = false
      break
    }
  }

  if (result) {
    console.log('Yes')
  } else {
    console.log('No')
  }
}

main(require("fs").readFileSync("/dev/stdin", "utf8"));


function main(input) {
    const args = input.split('\n');
    const N = parseInt(args[0], 10);
    const nums = args.slice(1, N + 1);
    const isValid = nums.every((n) => {
        var ns = n.split(' ');
        var t = parseInt(ns[0], 10),
            x = parseInt(ns[1], 10),
            y = parseInt(ns[2], 10);
        var sum = x + y;

        return (t >= sum) && ((t % 2) === (sum % 2));
    });

    if (isValid) {
        console.log('Yes');
    } else {
        console.log('No');
    }
}
main(require('fs').readFileSync('/dev/stdin', 'utf8'));


const main = input => {
  const inputList = input.split('\n')
  const count = parseInt(inputList[0], 10)
  const nums = inputList.slice(1, count + 1)
  const result = nums.every(n => {
    const arr = n.split(' ')
    const time = parseInt(arr[0], 10)
    const x = parseInt(arr[1], 10)
    const y = parseInt(arr[2], 10)
    const sum = x + y

    return (
      time >= sum &&
      time%2 === sum%2
    )
  })

  if (result) {
    console.log('Yes')
  } else {
  	console.log('No')
  }
}

main(require('fs').readFileSync('/dev/stdin', 'utf8'));


const input = require("fs").readFileSync("/dev/stdin", "utf8")
;(input => {

    const lines = input.split('\n')
    const N = lines[0] - 0

    const T = []
    for (let i = 1; i <= N; i++) {
         T.push(lines[i].split(' ').map(Number))
    }

    const f = (a, b) => {
      const dist = Math.abs(a[1] + a[2] - b[1] - b[2])
      const t = b[0] - a[0]
      if (t < dist) {
        return false
      } else if ((t - dist) % 2) {
        return false
      }
      return true
    }

    let ans = 'Yes'
    let t = null
    let p = [0, 0, 0]
    while (T.pop()) {
    }

    console.log(ans)

})(input)


const input = require("fs").readFileSync("/dev/stdin", "utf8")
;(input => {

    const lines = input.split('\n')
    const N = lines[0] - 0

    const T = []
    for (let i = 1; i <= N; i++) {
         T.push(lines[i].split(' ').map(Number))
    }

    const f = (a, b) => {
      const dist = Math.abs(a[1] + a[2] - b[1] - b[2])
      const t = b[0] - a[0]
      if (t < dist) {
        return false
      } else if ((t - dist) % 2) {
        return false
      }
      return true
    }

    let ans = 'Yes'
    let t = null
    let p = [0, 0, 0]
    while (T.shift()) {
    }

    console.log(ans)

})(input)


const input = require("fs").readFileSync("/dev/stdin", "utf8")
;(input => {

    const lines = input.split('\n')
    const N = lines[0] - 0

    const T = []
    for (let i = 1; i <= N; i++) {
         T.push(lines[i].split(' ').map(Number))
    }

    const f = (a, b) => {
      const dist = Math.abs(a[1] + a[2] - b[1] - b[2])
      const t = b[0] - a[0]
      if (t < dist) {
        return false
      } else if ((t - dist) % 2) {
        return false
      }
      return true
    }

    let ans = 'Yes'
    let t = null
    let p = [0, 0, 0]
    while (t = T.shift()) {
	    if (f(p, t)) {
            p = t
        } else {
            ans = 'No'
            break
        }
    }

    console.log(ans)

})(input)


package main

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

var sc = bufio.NewScanner(os.Stdin)

func r() (n int) {
	sc.Scan()
	for _, v := range sc.Bytes() {
		n = n*10 + int(v-48)
	}
	return
}

func abs(x int) int {
	if x < 0 {
		return -x
	} else {
		return x
	}
}

func main() {
	sc.Split(bufio.ScanWords)
	n := r()

	t, x, y := 0, 0, 0
	var tn, xn, yn int
	flg := true
	for i := 0; i < n; i++ {
		tn, xn, yn = r(), r(), r()
		dt, dx, dy := abs(tn-t), abs(xn-x), abs(yn-y)
		if !(dx+dy <= dt && (dx+dy)%2 == dt%2) {
			flg = false
		}
		t, x, y = tn, xn, yn
	}
	if flg {
		fmt.Println("Yes")
	} else {
		fmt.Println("No")
	}
}


// ProblemURL : https://atcoder.jp/contests/abc086/tasks/arc089_a
// ---------------------------------------------
package main

import (
	"bufio"
	"fmt"
	"math"
	"os"
	"sort"
	"strconv"
	"strings"
)

func abs(x int) int {
	if x < 0 {
		return -x
	}
	return x
}
func diff(a, b int) int {
	if a > b {
		return a - b
	}
	return b - a
}
func larger(a, b int) int {
	if a > b {
		return a
	}
	return b
}
func smaller(a, b int) int {
	if a < b {
		return a
	}
	return b
}
func largest(a, b, c int) (lgst int) {
	if a > b {
		lgst = a
	} else {
		lgst = b
	}
	if c > lgst {
		lgst = c
	}
	return
}
func smallest(a, b, c int) (slst int) {
	if a < b {
		slst = a
	} else {
		slst = b
	}
	if c < slst {
		slst = c
	}
	return
}
func intsMax(a []int) (val int) {
	if len(a) == 0 {
		panic("func intsMax: argument slice length must not be zero")
	}
	val = a[0]
	for _, aa := range a {
		if aa > val {
			val = aa
		}
	}
	return
}
func intsMaxIdx(a []int) (idx, val int) {
	if len(a) == 0 {
		panic("func intsMaxIdx: argument slice length must not be zero")
	}
	val = a[0]
	for i, aa := range a {
		if aa > val {
			idx, val = i, aa
		}
	}
	return
}
func intsMin(a []int) (val int) {
	if len(a) == 0 {
		panic("func intsMin: argument slice length must not be zero")
	}
	val = a[0]
	for _, aa := range a {
		if aa < val {
			val = aa
		}
	}
	return
}
func intsMinIdx(a []int) (idx, val int) {
	if len(a) == 0 {
		panic("func intsMinIdx: argument slice length must not be zero")
	}
	val = a[0]
	for i, aa := range a {
		if aa < val {
			idx, val = i, aa
		}
	}
	return
}
func intsSum(a []int) int {
	res := 0
	for _, v := range a {
		res += v
	}
	return res
}
func intsAve(s []int) float64 {
	return float64(intsSum(s)) / float64(len(s))
}
func intsAdd(ints *[]int, x int) { *ints = append(*ints, x) }
func intsJoin(a, b []int) []int  { return append(a, b...) }
func intsClear(a []int) []int    { return a[:0] }
func intsCopy(a []int) []int     { return append([]int(nil), a...) }
func intsCopySorted(a []int) []int {
	s := intsCopy(a)
	sort.Ints(s)
	return s
}
func intsReverse(a []int) {
	for i, j := 0, len(a)-1; i < j; i, j = i+1, j-1 {
		a[i], a[j] = a[j], a[i]
	}
	return
}
func intsFill(a []int, val int) {
	for i := 0; i < len(a); i++ {
		a[i] = val
	}
	return
}
func intsPeekBack(a []int) int {
	if len(a) == 0 {
		panic("func peekBack: zero length slice")
	}
	return a[len(a)-1]
}
func intsPeekFront(a []int) int {
	if len(a) == 0 {
		panic("func peekFront: zero length slice")
	}
	return a[0]
}
func intsPopBack(a *[]int) int {
	if len(*a) == 0 {
		panic("func popBack: zero length slice")
	}
	t := (*a)[len(*a)-1]
	*a = (*a)[:len(*a)-1]
	return t
}
func intsPopFront(a *[]int) int {
	if len(*a) == 0 {
		panic("func popFront: zero length slice")
	}
	h := (*a)[0]
	*a = (*a)[1:]
	return h
}
func intsPushBack(a *[]int, x int) { *a = append(*a, x) }
func intsPushFront(a *[]int, x int) {
	*a = append(*a, 0)
	copy((*a)[1:], (*a)[0:])
	(*a)[0] = x
}
func intsAppendSentinelHead(a *[]int, sentinel int) { intsPushFront(a, sentinel) }
func intsAppendSentinelTail(a *[]int, sentinel int) { intsPushBack(a, sentinel) }
func intsAppendSentinel(a *[]int, sentinel int) {
	intsPushFront(a, sentinel)
	intsPushBack(a, sentinel)
}
func isEven(n int) bool    { return n&1 == 0 }
func isOdd(n int) bool     { return n&1 == 1 }
func floor(x float64) int  { return int(x) }
func ceil(x float64) int   { return int(math.Ceil(x)) }
func ceilDiv(x, y int) int { return (x + y - 1) / y }
func pow(x, y int) int {
	if y < 0 {
		panic("Exponent must be a natural number")
	}
	z := 1
	for i := y; i != 0; i >>= 1 {
		if i&1 == 1 {
			z *= x
		}
		x *= x
	}
	return z
}
func fact(x int) int {
	fact := 1
	for i := 1; i <= x; i++ {
		fact *= i
	}
	return fact
}
func sigmaK(n int) int  { return n * (n + 1) / 2 }
func sigmaKK(n int) int { return (n * (n + 1) / 2) * (2*n + 1) / 3 }
func euclideanDistance(a, b point) float64 {
	s := diff(a.x, b.x)
	s *= s
	t := diff(a.y, b.y)
	t *= t
	return math.Sqrt(float64(s) + float64(t))
}
func manhattanDistance(a, b point) int {
	s := diff(a.x, b.x)
	t := diff(a.y, b.y)
	return s + t
}
func swap(a, b *int) { *a, *b = *b, *a }
func chmax(a *int, b int) {
	if *a < b {
		*a = b
	}
}
func chmin(a *int, b int) {
	if *a > b {
		*a = b
	}
}
func cumSum(a []int) []int {
	b := append([]int{0}, a...)
	for i := 1; i < len(b); i++ {
		b[i] += b[i-1]
	}
	return b
}
func runesReverse(a []rune) {
	for i, j := 0, len(a)-1; i < j; i, j = i+1, j-1 {
		a[i], a[j] = a[j], a[i]
	}
	return
}
func bytesReverse(a []byte) {
	for i, j := 0, len(a)-1; i < j; i, j = i+1, j-1 {
		a[i], a[j] = a[j], a[i]
	}
	return
}
func strUpperCase(s string) string { return strings.ToUpper(s) }
func strLowerCase(s string) string { return strings.ToLower(s) }
func strToInt(s string) int {
	i, err := strconv.Atoi(s)
	if err != nil {
		panic(err)
	}
	return i
}
func intToStr(i int) string  { return strconv.Itoa(i) }
func CalcMod(a, mod int) int { return (a%mod + mod) % mod }
func ModPow(x, y, mod int) int {
	if y < 0 {
		panic("Exponent must be a natural number")
	}
	z := 1
	for i := y; i != 0; i >>= 1 {
		if i&1 == 1 {
			z = (z * x) % mod
		}
		x = (x * x) % mod
	}
	return z
}
func ModFact(x, mod int) int {
	fact := 1
	for i := 1; i <= x; i++ {
		fact = fact * i % mod
	}
	return fact
}
func ModInv(x, mod int) int { return ModPow(x, mod-2, mod) }
func initMatrixBool(parentSize, childSize int, initialValue bool) *[][]bool {
	res := make([][]bool, parentSize)
	for i := range res {
		res[i] = make([]bool, childSize)
		for j := range res[i] {
			res[i][j] = initialValue
		}
	}
	return &res
}
func initMatrixInt(parentSize, childSize int, initialValue int) *[][]int {
	res := make([][]int, parentSize)
	for i := range res {
		res[i] = make([]int, childSize)
		for j := range res[i] {
			res[i][j] = initialValue
		}
	}
	return &res
}

var (
	sc = bufio.NewScanner(os.Stdin)
	bw = bufio.NewWriterSize(os.Stdout, bwBufSize)
)

func init() {
	sc.Split(bufio.ScanWords)
	sc.Buffer(make([]byte, 1e7), 1e7)
}
func ru() (n int) {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	for _, v := range sc.Bytes() {
		n = n*10 + int(v-48)
	}
	return
}
func ri() (n int) {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	b := sc.Bytes()
	neg := false
	if b[0] == 45 {
		neg = true
		b = b[1:]
	}
	for _, v := range b {
		n = n*10 + int(v-48)
	}
	if neg {
		n = -n
	}
	return
}
func ri64() (n int64) {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	b := sc.Bytes()
	neg := false
	if b[0] == 45 {
		neg = true
		b = b[1:]
	}
	for _, v := range b {
		n = n*10 + int64(v-48)
	}
	if neg {
		n = -n
	}
	return
}
func rf64() float64 {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	f, err := strconv.ParseFloat(sc.Text(), 64)
	if err != nil {
		panic(err)
	}
	return f
}
func rs() string {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	return sc.Text()
}
func rb() []byte {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	return sc.Bytes()
}
func rr() []rune {
	sc.Scan()
	if err := sc.Err(); err != nil {
		panic(err)
	}
	return []rune(sc.Text())
}
func ris(n int) []int {
	s := make([]int, n)
	for i := range s {
		s[i] = ri()
	}
	return s
}
func risZeroBased(n int) []int {
	s := make([]int, n)
	for i := range s {
		s[i] = ri() - 1
	}
	return s
}
func ri64s(n int) []int64 {
	s := make([]int64, n)
	for i := range s {
		s[i] = ri64()
	}
	return s
}
func rss(n int) []string {
	s := make([]string, n)
	for i := range s {
		s[i] = rs()
	}
	return s
}
func pf(format string, a ...interface{}) {
	if _, err := fmt.Fprintf(bw, format, a...); err != nil {
		panic(err)
	}
}
func pln(a ...interface{}) {
	if _, err := fmt.Fprintln(bw, a...); err != nil {
		panic(err)
	}
}
func pints(a []int) {
	for _, v := range a {
		fmt.Fprintln(bw, v)
	}
}
func pintsol(a []int) {
	s := fmt.Sprint(a)
	if _, err := fmt.Fprintln(bw, s[1:len(s)-1]); err != nil {
		panic(err)
	}
}
func dbg(a ...interface{}) {
	if _, err := fmt.Fprintln(os.Stderr, a...); err != nil {
		panic(err)
	}
}
func YESorNO(b bool) string {
	if b {
		return "YES"
	} else {
		return "NO"
	}
}
func YesOrNo(b bool) string {
	if b {
		return "Yes"
	} else {
		return "No"
	}
}
func main() {
	solve()
	bw.Flush()
}

const (
	bwBufSize = 1e6

	alphabetLower = "abcdefghijklmnopqrstuvwxyz"
	alphabetUpper = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"

	// maxInt64  = 9223372036854775807  // 9e18
	// maxInt32  = 2147483647           // 2e9
	// maxUint64 = 18446744073709551615 // 1e19
	inf = 1 << 60
	mod = 1e9 + 7
)

type pair struct{ fi, se int }
type byFiSe []pair

func (p byFiSe) Len() int      { return len(p) }
func (p byFiSe) Swap(i, j int) { p[i], p[j] = p[j], p[i] }
func (p byFiSe) Less(i, j int) bool {
	if p[i].fi == p[j].fi {
		return p[i].se < p[j].se
	}
	return p[i].fi < p[j].fi
}

type point struct{ x, y int }

func solve() {
	n := ri()
	ts := make([]int, n)
	xs := make([]int, n)
	ys := make([]int, n)
	for i := 0; i < n; i++ {
		ts[i] = ri()
		xs[i] = ri()
		ys[i] = ri()
	}

	prevT := 0
	prevX := 0
	prevY := 0
	ok := true
	for i := 0; i < n; i++ {
		dist := manhattanDistance(point{prevX, prevY}, point{xs[i], ys[i]})
		time := ts[i] - prevT
		rest := time - dist
		if !(rest >= 0 && isEven(rest)) {
			ok = false
			break
		}
		prevT = ts[i]
		prevX = xs[i]
		prevY = ys[i]
	}
	pln(YesOrNo(ok))
}


package main

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

var sc = bufio.NewScanner(os.Stdin)

func Scan() string {
	sc.Scan()
	return sc.Text()
}
func iScan() int {
	n, _ := strconv.Atoi(Scan())
	return n
}
func fScan() float64 {
	n, _ := strconv.ParseFloat(Scan(), 64)
	return n
}
func stringToInt(s string) int {
	n, _ := strconv.Atoi(s)
	return n
}
func SScan(n int) []string {
	a := make([]string, n)
	for i := 0; i < n; i++ {
		a[i] = Scan()
	}
	return a
}
func iSScan(n int) []int {
	a := make([]int, n)
	for i := 0; i < n; i++ {
		a[i] = iScan()
	}
	return a
}
func abs(x int) int {
	if x < 0 {
		x = -x
	}
	return x
}
func larger(a, b int) int {
	if a < b {
		return b
	} else {
		return a
	}
}
func smaller(a, b int) int {
	if a > b {
		return b
	} else {
		return a
	}
}
func max(a []int) int {
	x := a[0]
	for i := 0; i < len(a); i++ {
		if x < a[i] {
			x = a[i]
		}
	}
	return x
}
func min(a []int) int {
	x := a[0]
	for i := 0; i < len(a); i++ {
		if x > a[i] {
			x = a[i]
		}
	}
	return x
}
func sum(a []int) int {
	x := 0
	for _, v := range a {
		x += v
	}
	return x
}

var mod int = 1000000007

func main() {
	buf := make([]byte, 0)
	sc.Buffer(buf, mod)
	sc.Split(bufio.ScanWords)
	n := iScan()
	t, x, y := 0, 0, 0
	f := true
	for i := 0; i < n; i++ {
		p, q, r := iScan(), iScan(), iScan()
		c := abs(p - t)
		d := abs(q-x) + abs(r-y)
		if c%2 != d%2 || d > c {
			f = false
		}
		t, x, y = p, q, r
	}
	if f {
		fmt.Println("Yes")
	} else {
		fmt.Println("No")
	}
}


package main

import(
	"fmt"
)

func main(){
  var num int
  var slct, slcx, slcy []int
  var ans bool
  var i int = 0

	num = fmt.Scanf("%d\n", &num)
  	for num > i {
    	fmt.Scanf("%d %d %d\n", &slct[i], &slcx[i], &slcy[i])
    	i++
	}

  var diff int = slct[num] - slcx[num] - slcy[num]
  i = 0
  for num > i {
    if diff % 2 != 0 {
		ans = false
      	break
    }
    i++
  }
  fmt.Println(ans)
}


package main

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

var (
	sc = bufio.NewReader(os.Stdin)
)

type pos struct {
	t, x, y int
}

func (p *pos) arrive(p2 *pos) bool {
	t := p.t - p2.t
	x := p.x - p2.x
	y := p.y - p2.y
	if x+y == t {
		return true
	}
	if x+y < t {
		if (t-(x+y))%2 == 0 {
			return true
		} else {
			return false
		}
	}
	if t < x+y {
		return false
	}
	return true
}

func main() {
	N := scanInt()
	c := &pos{t: 0, x: 0, y: 0}
	for i := 0; i < N; i++ {
		n := &pos{t: scanInt(), x: scanInt(), y: scanInt()}
		if !n.arrive(c) {
			fmt.Println("No")
			return
		}
		c = n
	}
	fmt.Println("Yes")
}

func scan(a ...interface{}) { _, err := fmt.Fscan(sc, a...); pnc(err) }
func scanStr() (s string)   { scan(&s); return }
func scanInt() int          { i, err := strconv.Atoi(scanStr()); pnc(err); return i }
func scanFloat() float64    { f, err := strconv.ParseFloat(scanStr(), 64); pnc(err); return f }
func pnc(err error) {
	if err != nil {
		panic(err)
	}
}


package main

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

var (
	sc = bufio.NewReader(os.Stdin)
)

type pos struct {
	t, x, y int
}

func (p *pos) arrive(p2 *pos) bool {
	t := p.t - p2.t
	x := p.x - p2.x
	y := p.y - p2.y
	if x+y == t {
		return true
	}
	if x+y < t && (t-(x+y))%2 == 0 {
		return true
	}
	if x+y < t && (t-(x+y))%2 == 1 {
		return false
	}
	if x+y == 1 && t%2 == 0 {
		return false
	}
	if x+y > t {
		return false
	}
	return true
}

func main() {
	N := scanInt()
	c := &pos{t: 0, x: 0, y: 0}
	for i := 0; i < N; i++ {
		n := &pos{t: scanInt(), x: scanInt(), y: scanInt()}
		if !n.arrive(c) {
			fmt.Println("No")
			return
		}
		if !rec(c, n) {
			fmt.Println("No")
			return
		}
		c = n
	}
	fmt.Println("Yes")
}

func rec(c, n *pos) bool {
	if !n.arrive(c) {
		return false
	}
	if c.t == n.t {
		if c.x == n.x && c.y == n.y {
			return true
		} else {
			return false
		}
	}
	// x+1, y
	if rec(&pos{t: c.t + 1, x: c.x + 1, y: c.y}, n) {
		return true
	}
	// x-1, y
	if rec(&pos{t: c.t + 1, x: c.x - 1, y: c.y}, n) {
		return true
	}
	// x, y+1
	if rec(&pos{t: c.t + 1, x: c.x, y: c.y + 1}, n) {
		return true
	}
	// x, y-1
	if rec(&pos{t: c.t + 1, x: c.x, y: c.y - 1}, n) {
		return true
	}

	return false
}

func scan(a ...interface{}) { _, err := fmt.Fscan(sc, a...); pnc(err) }
func scanStr() (s string)   { scan(&s); return }
func scanInt() int          { i, err := strconv.Atoi(scanStr()); pnc(err); return i }
func scanFloat() float64    { f, err := strconv.ParseFloat(scanStr(), 64); pnc(err); return f }
func pnc(err error) {
	if err != nil {
		panic(err)
	}
}


# n
# t x y

n = gets.to_i
t = []
x = []
y = []

t << 0
x << 0
y << 0
n.times do
  t_temp, x_temp, y_temp = gets.split
  t << t_temp.to_i
  x << x_temp.to_i
  y << y_temp.to_i
end

def move_enable?(t_from, t_to, x_from, x_to, y_from, y_to)
  t_dif = t_to - t_from
  x_dif = (x_to - x_from).abs
  y_dif = (y_to - y_from).abs
  if t_dif < x_dif + y_dif
    return false
  elsif t_dif == x_dif + y_dif
    return true
  elsif ( t_dif - (x_dif + y_dif) ).even?
    return true
  else
    return false
  end
end

flag = "No"
n.times do |i|
  flag_temp = move_enable?(t[i], t[i+1], x[i], x[i+1], y[i], y[i+1])
  break unless flag_temp
  flag = "Yes" if i == n-1
end

puts flag


N=gets.to_i
px=py=pt=0
r=true
N.times{
    t,x,y=gets.split.map(&:to_i)
    dx=(x-px).abs
    dy=(y-py).abs
    dt=(t-pt).abs
    if dx+dy>dt
        r=false
    end
    if (dx+dy) % 2 != dt % 2
        r=false
    end
    px=x
    py=y
    pt=t
}
puts r ? "Yes" : "No"


gets
current = [0, 0, 0]
ARGF.each do |line|
  t, x, y = line.split.map(&:to_i)
  d = (current[1] - x).abs + (current[2] -y).abs
  if t - current[0] < d
	  puts 'No'
  	  exit
  else
    unless t.even? == (x + y).even?
      puts 'No'
      exit
    end
  end
end
puts 'Yes'


N = gets.to_i
t,x,y = N.times.map{gets.split.map(&:to_i)}.transpose
nowx = 0
nowy = 0
nowt = 0
N.times do |i|
  d = (x[i]-nowx).abs + (y[i]-nowy).abs
  nowt = t[i] - nowt
  if (nowt.odd? && d.even?) || (nowt.even? && d.odd?) || nowt < d
    puts "No"
    exit
  end
  nowx = x[i]
  nowy = y[i]
end
puts "Yes"


# n
# t x y

n = gets.to_i
t = []
x = []
y = []

t << 0
x << 0
y << 0
n.times do
  t_temp, x_temp, y_temp = gets.split
  t << t_temp.to_i
  x << x_temp.to_i
  y << y_temp.to_i
end

def move_enable?(t_from, t_to, x_from, x_to, y_from, y_to)
  t_dif = t_to - t_from
  x_dif = x_to - x_from
  y_dif = y_to - y_from
  if t_dif < x_dif + y_dif
    return false
  elsif t_dif == x_dif + y_dif
    return true
  elsif ( t_dif - (x_dif + y_dif) ).even?
    return true
  else
    return false
  end
end

flag = "No"
n.times do |i|
  flag_temp = move_enable?(t[i], t[i+1], x[i], x[i+1], y[i], y[i+1])
  break unless flag_temp
  flag = "Yes" if i == n-1
end

puts flag


# n
# t x y

n = gets.to_i
t = []
x = []
y = []

t << 0
x << 0
y << 0
n.times do
  t_temp, x_temp, y_temp = gets.split
  t << t_temp.to_i
  x << x_temp.to_i
  y << y_temp.to_i
end

def move_enable?(t_from, t_to, x_from, x_to, y_from, y_to)
  t_dif = t_to - t_from
  x_dif = x_to - x_from
  y_dif = y_to - y_from
  if t_dif < x_dif + y_dif
    return false
  elsif t_dif == x_dif + y_dif
    return true
  elsif ( t_dif - (x_dif - y_dif) ).even?
    return true
  else
    return false
  end
end

flag = "No"
n.times do |i|
  flag_temp = move_enable?(t[i], t[i+1], x[i], x[i+1], y[i], y[i+1])
  break unless flag_temp
  flag = "Yes" if i == n-1
end

puts flag


use std::io::stdin;
use std::vec::Vec;

mod utils {
    use std::io::BufRead;
    use std::str::{self, FromStr};

    pub struct StdinReader<R: BufRead> {
        reader: R,
        buf: Vec<u8>,
    }

    impl<R: BufRead> StdinReader<R> {
        pub fn new(reader: R) -> StdinReader<R> {
            StdinReader {
                reader: reader,
                buf: Vec::new(),
            }
        }

        #[allow(unused)]
        #[inline]
        pub fn reads<T: FromStr>(&mut self) -> T {
            self.read_until(b' ')
        }

        #[allow(unused)]
        #[inline]
        pub fn readl<T: FromStr>(&mut self) -> T {
            self.read_until(b'\n')
        }

        #[allow(unused)]
        #[inline]
        pub fn read_vec<T: FromStr>(&mut self) -> Vec<T> {
            return self.read_until::<String>(b'\n').trim().split_whitespace().map(|c| c.parse().ok().unwrap()).collect();
        }

        #[inline]
        pub fn read_until<T: FromStr>(&mut self, delim: u8) -> T {
            loop {
                self.buf.clear();
                let len = self.reader
                    .read_until(delim, &mut self.buf)
                    .expect("failed reading bytes");
                match len {
                    0 => panic!("early eof"),
                    1 if self.buf[0] == delim => (),
                    _ => {
                        if self.buf[len - 1] == delim {
                            self.buf.truncate(len - 1);
                        }
                        break;
                    }
                }
            }

            let elem = unsafe { str::from_utf8_unchecked(&self.buf) };
            elem.parse().unwrap_or_else(|_| panic!(format!("failed parsing: {}", elem)))
         }
    }
}

fn main(){
    let stdin = stdin();
    let mut r = utils::StdinReader::new(stdin.lock());
    let mut n:usize = r.readl();

    let mut res = "Yes";

    let mut pre_x = 0;
    let mut pre_y = 0;
    let mut pre_t = 0;

    for _ in 0..n {
        let t:i32 = r.reads();
        let x:i32 = r.reads();
        let y:i32 = r.readl();

        if( ((t - pre_t) - (x - pre_x).abs() - (y - pre_y).abs()) >= 0 && ((t - pre_t) - (x - pre_x).abs() - (y - pre_y).abs()) % 2 == 0 ){
            pre_x = x;
            pre_y = y;
            pre_t = t;
        }else{
            res = "No";
            break
        }
    }

    println!("{}",res);
}