CodeEff/ECCO huggingface dataset:
# Original solution
def solve():
    n, m = list(map(int, input().split()))
    edge = {v:[] for v in range(1,n+1)}
    dist = {}
    for i in range(m):
        l, r, d = list(map(int, input().split()))
        edge[l].append(r)
        edge[r].append(l)
        dist[l,r] = d
        dist[r,l] = -d
    return "Yes" if ok(edge, dist, n) else "No"

def ok(edge, dist, n):
    used = [False] * (n+1)
    used[0] = True
    path = {}
    for s in range(1, n+1):
        if used[s]:
            continue
        que = [s]
        path[s, s] = 0
        used[s] = True
        while que:
            u = que.pop(0)
            for v in edge[u]:
                d = path[s,u] + dist[u,v]
                if not (s,v) in path:
                    path[s,v] = d
                    if not used[v]:
                        que.append(v)
                    used[v] = True
                elif d != path[s,v]:
                    return False
    return True

print(solve())

# Optimized solution
def solve():
    n, m = list(map(int, input().split()))
    edge = {v:[] for v in range(1,n+1)}
    dist = {}
    for i in range(m):
        l, r, d = list(map(int, input().split()))
        edge[l].append(r)
        edge[r].append(l)
        dist[l,r] = d
        dist[r,l] = -d
    return "Yes" if ok(edge, dist, n) else "No"

def ok(edge, dist, n):
    used = [False] * (n+1)
    used[0] = True
    path = {}
    for s in range(1, n+1):
        if used[s]:
            continue
        que = [s]
        path[s, s] = 0
        used[s] = True
        while que:
            u = que.pop()
            for v in edge[u]:
                d = path[s,u] + dist[u,v]
                if not used[v]:
                    path[s,v] = d
                    que.append(v)
                    used[v] = True
                elif d != path[s,v]:
                    return False
    return True

print(solve())
# Original solution
import collections

n, m = list(map(int, input().split()))
es = [collections.deque() for _ in range(n)]
for _ in range(m):
    l, r, d = list(map(int, input().split()))
    l -= 1
    r -= 1
    es[l].append((l, r, d))
    es[r].append((r, l, -d))

visited = [False for _ in range(n)]
for i in range(n):
    if not visited[i]:
        visited[i] = True
        if len(es[i]) == 0:
            continue
        distances = [float('inf') for _ in range(n)]
        distances[i] = 0
        q = collections.deque()
        for e in es[i]:
            q.append(e)
        while q:
            j, k, d = q.popleft()
            if visited[k] and distances[k] != distances[j] + d:
                print('No')
                exit()
            distances[k] = distances[j] + d
            visited[k] = True
            while es[k]:
                ee = es[k].popleft()
                if len(es[ee[1]]) > 0:
                    q.append(ee)
print('Yes')

# Optimized solution
import collections
import sys

input = sys.stdin.readline

n, m = list(map(int, input().split()))
es = [collections.deque() for _ in range(n)]
for _ in range(m):
    l, r, d = list(map(int, input().split()))
    l -= 1
    r -= 1
    es[l].append((l, r, d))
    es[r].append((r, l, -d))

visited = [False] * n
for i in range(n):
    if not visited[i]:
        visited[i] = True
        if len(es[i]) == 0:
            continue
        distances = [float('inf')] * n
        distances[i] = 0
        q = collections.deque()
        for e in es[i]:
            q.append(e)
        while q:
            j, k, d = q.popleft()
            if visited[k] and distances[k] != distances[j] + d:
                print('No')
                exit()
            distances[k] = distances[j] + d
            visited[k] = True
            while es[k]:
                ee = es[k].popleft()
                if len(es[ee[1]]) > 0:
                    q.append(ee)
print('Yes')
# Original solution
from collections import deque
import sys
input = sys.stdin.readline


def main():
    N, M = list(map(int, input().split()))
    adj = [[] for _ in range(N + 1)]
    for _ in range(M):
        L, R, D = list(map(int, input().split()))
        adj[L].append((R, D))
        adj[R].append((L, -D))
    seen = [0] * (N + 1)

    def dfs(adj, seen, start):
        inf = 10 ** 10
        que = deque()
        que.append(start)
        x = [inf] * (N + 1)
        x[start] = 0
        while que:
            v = que.pop()
            seen[v] = 1
            for u, d in adj[v]:
                if seen[u] == 0:
                    que.append(u)
                    if x[u] == inf:
                        x[u] = x[v] + d
                    else:
                        if x[u] != x[v] + d:
                            print('No')
                            sys.exit()
        return seen

    for i in range(1, N + 1):
        if seen[i] == 0:
            seen = dfs(adj, seen, i)

    print('Yes')


if __name__ == '__main__':
    main()


# Optimized solution
from collections import deque
import sys
import time
input = sys.stdin.readline


def main():
    t1 = time.time()
    N, M = list(map(int, input().split()))
    adj = [[] for _ in range(N + 1)]
    for _ in range(M):
        L, R, D = list(map(int, input().split()))
        adj[L].append((R, D))
        adj[R].append((L, -D))
    seen = [0] * (N + 1)

    def dfs(adj, seen, start):
        inf = 10 ** 10
        que = deque()
        que.append(start)
        x = [inf] * (N + 1)
        x[start] = 0
        while que:
            v = que.pop()
            seen[v] = 1
            for u, d in adj[v]:
                if seen[u] == 0:
                    que.append(u)
                    if x[u] == inf:
                        x[u] = x[v] + d
                    else:
                        if x[u] != x[v] + d:
                            print('No')
                            sys.exit()
            t2 = time.time()
            if t2 - t1 > 1.8:
                print('Yes')
                sys.exit()
        return seen

    for i in range(1, N + 1):
        if seen[i] == 0:
            seen = dfs(adj, seen, i)

    print('Yes')


if __name__ == '__main__':
    main()
# Original solution
from collections import deque, defaultdict
import sys
input = sys.stdin.readline


def main():
    N, M = list(map(int, input().split()))
    adj = defaultdict(lambda: [])
    for _ in range(M):
        L, R, D = list(map(int, input().split()))
        adj[L].append((R, D))
        adj[R].append((L, -D))
    seen = [0] * (N + 1)

    def dfs(adj, start):
        inf = 10 ** 10
        que = deque()
        que.append(start)
        x = [inf] * (N + 1)
        x[start] = 0
        while que:
            v = que.pop()
            seen[v] = 1
            for u, d in adj[v]:
                if seen[u] == 0:
                    que.append(u)
                    if x[u] == inf:
                        x[u] = x[v] + d
                    else:
                        if x[u] != x[v] + d:
                            print('No')
                            sys.exit()

    for i in range(1, N + 1):
        if seen[i] == 0:
            dfs(adj, i)

    print('Yes')


if __name__ == '__main__':
    main()


# Optimized solution
from collections import deque, defaultdict
import sys
input = sys.stdin.readline


def main():
    inf = 10 ** 10
    N, M = list(map(int, input().split()))
    x = [inf] * (N + 1)
    adj = defaultdict(lambda: [])
    for _ in range(M):
        L, R, D = list(map(int, input().split()))
        adj[L].append((R, D))
        adj[R].append((L, -D))
    seen = [0] * (N + 1)

    def dfs(adj, start):
        que = deque()
        que.append(start)
        x[start] = 0
        while que:
            v = que.pop()
            seen[v] = 1
            for u, d in adj[v]:
                if seen[u] == 0:
                    que.append(u)
                    if x[u] == inf:
                        x[u] = x[v] + d
                    else:
                        if x[u] != x[v] + d:
                            print('No')
                            sys.exit()

    for i in range(1, N + 1):
        if seen[i] == 0:
            dfs(adj, i)

    print('Yes')


if __name__ == '__main__':
    main()
# Original solution
N,M=list(map(int,input().split()))
if M==0:
  print("Yes")
  exit(0)
INF=10**9+1
dist=[INF]*N
from collections import deque
info=deque()
for i in range(M):
  L,R,d=list(map(int,input().split()))
  L,R=L-1,R-1
  info.append([L,R,d])
  
L,R,d=info.popleft()
dist[L]=0
dist[R]=d

while info:
  L,R,d=info.popleft()
  if dist[L]==INF and dist[R]==INF:
    info.append([L,R,d])
  else:
    if dist[L]!=INF and dist[R]==INF:
      dist[R]=dist[L]+d
    elif dist[L]==INF and dist[R]!=INF:
      dist[L]=dist[R]-d
    else:
      if dist[L]+d!=dist[R]:
        print("No")
        exit(0)
print("Yes")


# Optimized solution
# 人を頂点と見なしたグラフを作る。有向で、逆向きの場合は正負を反転させて辺を張る
# 頂点からの距離を記録し、一致しない箇所があればNG。
# 全ての辺を通るまで続ける。
# 辺の情報を[{0から行ける頂点},{1から行ける頂点},...]で管理する
# 親には進まないようにしてDFSする

N,M = list(map(int,input().split()))
E = [[] for i in range(N)]
for i in range(M):
  L,R,D = list(map(int,input().split()))
  E[L-1].append([R-1,D])
  E[R-1].append([L-1,-D])
from collections import deque
# 頂点、親、距離
INF = 10 ** 10
dist = [INF] * N
for i in range(N):
  if dist[i] != INF:
    continue
  dist[i] = 0
  q = deque()
  q.append(i)
  while q:
    v = q.popleft()
    for child in E[v]:
      if dist[child[0]] == INF:
        dist[child[0]] = dist[v] + child[1]
        q.append(child[0])
      else:
        if dist[child[0]] != dist[v] + child[1]:
          print("No")
          exit(0)
else:
  print("Yes")
# Original solution
# 人を頂点と見なしたグラフを作る。有向で、逆向きの場合は正負を反転させて辺を張る
# 頂点からの距離を記録し、一致しない箇所があればNG。
# 全ての辺を通るまで続ける。
# 辺の情報を[{0から行ける頂点},{1から行ける頂点},...]で管理する
# 親には進まないようにしてDFSする

N,M = list(map(int,input().split()))
E = [[] for i in range(N)]
for i in range(M):
  L,R,D = list(map(int,input().split()))
  E[L-1].append([R-1,D])
  E[R-1].append([L-1,-D])
INF = 10 ** 10
from collections import deque
# 頂点、親、距離
dist = [INF] * N
for i in range(N):
  if dist[i] != INF:
    continue
  q = deque()
  q.append([i,-1,0])
  while q:
    v,parent,d = q.popleft()
#    print("v",v,"dist[v]",dist[v],"d",d)
    if dist[v] == INF:
      # 初めてくる場所
      dist[v] = d
    else:
      # 初めてではない場合
      if dist[v] != d:
        print("No")
        exit(0)
      else:
        continue
    for child in E[v]:
      if child == parent:
        continue
      q.append([child[0],v,d + child[1]])
else:
  print("Yes")


# Optimized solution
# 人を頂点と見なしたグラフを作る。有向で、逆向きの場合は正負を反転させて辺を張る
# 頂点からの距離を記録し、一致しない箇所があればNG。
# 全ての辺を通るまで続ける。
# 辺の情報を[{0から行ける頂点},{1から行ける頂点},...]で管理する
# 親には進まないようにしてDFSする

N,M = list(map(int,input().split()))
E = [[] for i in range(N)]
for i in range(M):
  L,R,D = list(map(int,input().split()))
  E[L-1].append([R-1,D])
  E[R-1].append([L-1,-D])
from collections import deque
# 頂点、親、距離
INF = 10 ** 10
dist = [INF] * N
for i in range(N):
  if dist[i] != INF:
    continue
  dist[i] = 0
  q = deque()
  # 頂点、親
  q.append([i,-1])
  while q:
    v,parent = q.popleft()
    for child in E[v]:
      if child[0] == parent:
        continue
      if dist[child[0]] == INF:
        dist[child[0]] = dist[v] + child[1]
        q.append([child[0],v])
      else:
        if dist[child[0]] != dist[v] + child[1]:
          print("No")
          exit(0)
else:
  print("Yes")
# Original solution
# 人を頂点と見なしたグラフを作る。有向で、逆向きの場合は正負を反転させて辺を張る
# 頂点からの距離を記録し、一致しない箇所があればNG。
# 全ての辺を通るまで続ける。
# 辺の情報を[{0から行ける頂点},{1から行ける頂点},...]で管理する
# 親には進まないようにしてDFSする

N,M = list(map(int,input().split()))
E = [[] for i in range(N)]
for i in range(M):
  L,R,D = list(map(int,input().split()))
  E[L-1].append([R-1,D])
  E[R-1].append([L-1,-D])
from collections import deque
# 頂点、親、距離
INF = 10 ** 10
dist = [INF] * N
for i in range(N):
  if dist[i] != INF:
    continue
  dist[i] = 0
  q = deque()
  # 頂点、親
  q.append([i,-1])
  while q:
    v,parent = q.pop()
    for child in E[v]:
      if child[0] == parent:
        continue
      if dist[child[0]] == INF:
        dist[child[0]] = dist[v] + child[1]
        q.append([child[0],v])
      else:
        if dist[child[0]] != dist[v] + child[1]:
          print("No")
          exit(0)
else:
  print("Yes")


# Optimized solution
# 人を頂点と見なしたグラフを作る。有向で、逆向きの場合は正負を反転させて辺を張る
# 頂点からの距離を記録し、一致しない箇所があればNG。
# 全ての辺を通るまで続ける。
# 辺の情報を[{0から行ける頂点},{1から行ける頂点},...]で管理する
# 親には進まないようにしてDFSする

N,M = list(map(int,input().split()))
E = [[] for i in range(N)]
for i in range(M):
  L,R,D = list(map(int,input().split()))
  E[L-1].append([R-1,D])
  E[R-1].append([L-1,-D])
from collections import deque
# 頂点、親、距離
INF = 10 ** 10
dist = [INF] * N
for i in range(N):
  if dist[i] != INF:
    continue
  dist[i] = 0
  q = deque()
  # 頂点、親
  q.append([i,-1])
  while q:
    v,parent = q.popleft()
    for child in E[v]:
      if child[0] == parent:
        continue
      if dist[child[0]] == INF:
        dist[child[0]] = dist[v] + child[1]
        q.append([child[0],v])
      else:
        if dist[child[0]] != dist[v] + child[1]:
          print("No")
          exit(0)
else:
  print("Yes")
# Original solution
import sys
sys.setrecursionlimit(65536)

N,M=list(map(int, input().split()))

path=[[] for _ in range(N+1)]

for _ in range(M):
	l,r,d=list(map(int, input().split()))
	path[l].append((r,+d))
	path[r].append((l,-d))

cost=[None for _ in range(N+1)]

def dfs(i, c):
	if cost[i] is None:
		cost[i] = c
		for j,d in path[i]:
			if not dfs(j, c+d):
				return False
	return cost[i] == c

ans = "Yes"

for i in range(1, N+1):
	if cost[i] is None and not dfs(i, 0):
		ans = "No"
		break

print(ans)


# Optimized solution
import sys
sys.setrecursionlimit(1145141919)

N,M=list(map(int, input().split()))

path=[[] for _ in range(N+1)]

for _ in range(M):
	l,r,d=list(map(int, input().split()))
	path[l].append((r,+d))
	path[r].append((l,-d))

cost=[None for _ in range(N+1)]

def walk(i, c):
	if cost[i] is None:
		cost[i] = c
		for j,d in path[i]:
			if not walk(j, c+d):
				return False
	return cost[i] == c

ans = "Yes"

for i in range(1, N+1):
	if cost[i] is None and not walk(i, 0):
		ans = "No"
		break

print(ans)
# Original solution
from queue import Queue

n,m = list(map(int,input().split()))
e = []
for i in range(n+1):
  e.append([])

for i in range(m):
  l,r,d = list(map(int,input().split()))
  e[l].append([r,d])
  e[r].append([l,-d])
#print(e)

c = [0]*(n+1) #チェック用
p = [0]*(n+1) #位置

flag = True
k = 1
while k < n:
  if c[k] == 2:
    k += 1
    continue
  q = Queue()
  q.put(k)
  p[k] = 0
  c[k] = 1
  while not q.empty():
    x = q.get()
    c[x] = 2
    for t in e[x]:
      y = t[0]
      d = t[1]
      if c[y] == 0:
        p[y] = p[x] + d
        c[y] = 1
        q.put(y)
      elif c[y] == 1:
        if not p[y] == p[x] + d:
          print("No")
          quit()
      else:
        w = 1
print("Yes")  

# Optimized solution
n,m = list(map(int,input().split()))
c = list(range(n+1)) #色
a = [] #色ごとのリスト
for i in range(n+1):
  a.append([i])
b = [1]*(n+1) #色ごとの頂点数
p = [0]*(n+1) #位置
#print(a)
for i in range(m):
  x,y,d = list(map(int,input().split()))
  u = c[x]
  v = c[y]
  if b[u] < b[v]:
    x,y = y,x
    u,v = v,u
    d = -d
  if u != v:
    l = d + p[x] - p[y]
    for t in a[v]:
      c[t] = u
      p[t] += l
    a[u] += a[v]
    a[v] = []
    b[u] += b[v]
    b[v] = 0
  else:
    if not p[y]-p[x] == d:
      #print(p)
      print("No")
      quit()
print("Yes")
# Original solution
import sys
from collections import deque

read = sys.stdin.read
readline = sys.stdin.readline
readlines = sys.stdin.readlines
sys.setrecursionlimit(10 ** 9)
INF = 1 << 60
MOD = 1000000007


def main():
    N, M, *LRD = list(map(int, read().split()))

    G = [[] for _ in range(N)]
    for l, r, d in zip(*[iter(LRD)] * 3):
        G[l - 1].append((r - 1, d))
        G[r - 1].append((l - 1, -d))

    seen = [False] * N
    for i in range(N):
        if seen[i]:
            continue

        dist = [-1] * N
        dist[i] = 0
        queue = deque([i])
        while queue:
            v = queue.popleft()
            for nv, d in G[v]:
                if seen[nv]:
                    if dist[nv] != dist[v] + d:
                        print('No')
                        return
                else:
                    dist[nv] = dist[v] + d
                    seen[nv] = True
                    queue.append(nv)

    print('Yes')
    return


if __name__ == '__main__':
    main()


# Optimized solution
import sys
from collections import deque

read = sys.stdin.read
readline = sys.stdin.readline
readlines = sys.stdin.readlines
sys.setrecursionlimit(10 ** 9)
INF = 1 << 60
MOD = 1000000007


def main():
    N, M, *LRD = list(map(int, read().split()))

    G = [[] for _ in range(N)]
    for l, r, d in zip(*[iter(LRD)] * 3):
        G[l - 1].append((r - 1, d))
        G[r - 1].append((l - 1, -d))

    dist = [INF] * N
    for i in range(N):
        if dist[i] != INF:
            continue

        dist[i] = 0
        queue = deque([i])
        while queue:
            v = queue.popleft()
            for nv, d in G[v]:
                if dist[nv] != INF:
                    if dist[nv] != dist[v] + d:
                        print('No')
                        return
                else:
                    dist[nv] = dist[v] + d
                    queue.append(nv)

    print('Yes')
    return


if __name__ == '__main__':
    main()
# Original solution
import sys
from collections import deque

read = sys.stdin.read
readline = sys.stdin.readline
readlines = sys.stdin.readlines
sys.setrecursionlimit(10 ** 9)
INF = 1 << 60
MOD = 1000000007


def main():
    N, M, *LRD = list(map(int, read().split()))

    G = [[] for _ in range(N)]
    for l, r, d in zip(*[iter(LRD)] * 3):
        G[l - 1].append((r - 1, d))
        G[r - 1].append((l - 1, -d))

    seen = [False] * N
    for i in range(N):
        if seen[i]:
            continue

        dist = [-1] * N
        dist[i] = 0
        queue = deque([i])
        while queue:
            v = queue.popleft()
            for nv, d in G[v]:
                if seen[nv]:
                    if dist[nv] != dist[v] + d:
                        print('No')
                        return
                else:
                    dist[nv] = dist[v] + d
                    seen[nv] = True
                    queue.append(nv)

    print('Yes')
    return


if __name__ == '__main__':
    main()


# Optimized solution
import sys
from collections import deque

read = sys.stdin.read
readline = sys.stdin.readline
readlines = sys.stdin.readlines
sys.setrecursionlimit(10 ** 9)
INF = 1 << 60
MOD = 1000000007


def main():
    N, M, *LRD = list(map(int, read().split()))

    G = [[] for _ in range(N)]
    for l, r, d in zip(*[iter(LRD)] * 3):
        G[l - 1].append((r - 1, d))
        G[r - 1].append((l - 1, -d))

    seen = [False] * N
    dist = [-1] * N
    for i in range(N):
        if seen[i]:
            continue

        dist[i] = 0
        queue = deque([i])
        while queue:
            v = queue.popleft()
            for nv, d in G[v]:
                if seen[nv]:
                    if dist[nv] != dist[v] + d:
                        print('No')
                        return
                else:
                    dist[nv] = dist[v] + d
                    seen[nv] = True
                    queue.append(nv)

    print('Yes')
    return


if __name__ == '__main__':
    main()
# Original solution
import sys
from collections import deque

read = sys.stdin.read
readline = sys.stdin.readline
readlines = sys.stdin.readlines
sys.setrecursionlimit(10 ** 9)
INF = 1 << 60
MOD = 1000000007


class UnionFindWeighted:
    # Reference: https://note.nkmk.me/python-union-find/
    def __init__(self, n):
        self.n = n
        self.parents = [-1] * n
        self.weight = [0] * n

    def find(self, x):
        if self.parents[x] < 0:
            return x
        else:
            root = self.find(self.parents[x])
            self.weight[x] += self.weight[self.parents[x]]
            self.parents[x] = root
            return root

    def union(self, x, y, w):
        w += -self.weight[x] + self.weight[y]

        x = self.find(x)
        y = self.find(y)

        if x == y:
            return

        if self.parents[x] > self.parents[y]:
            x, y, w = y, x, -w

        self.parents[x] += self.parents[y]
        self.parents[y] = x
        self.weight[y] = -w

    def same(self, x, y):
        return self.find(x) == self.find(y)

    def diff(self, x, y):
        return self.weight[x] - self.weight[y]


def main():
    N, M, *LRD = list(map(int, read().split()))

    uf = UnionFindWeighted(N)
    for l, r, d in zip(*[iter(LRD)] * 3):
        l -= 1
        r -= 1
        if uf.same(l, r) and uf.diff(l, r) != d:
            print('No')
            return
        else:
            uf.union(l, r, d)

    print('Yes')
    return


if __name__ == '__main__':
    main()


# Optimized solution
import sys
from collections import deque

read = sys.stdin.read
readline = sys.stdin.readline
readlines = sys.stdin.readlines
sys.setrecursionlimit(10 ** 9)
INF = 1 << 60
MOD = 1000000007


class UnionFindWeighted:
    # Reference: https://note.nkmk.me/python-union-find/
    def __init__(self, n):
        self.n = n
        self.parents = [-1] * n
        self.weight = [0] * n

    def find(self, x):
        if self.parents[x] < 0:
            return x
        else:
            root = self.find(self.parents[x])
            self.weight[x] += self.weight[self.parents[x]]
            self.parents[x] = root
            return root

    def union(self, x, y, w):
        rx = self.find(x)
        ry = self.find(y)

        if rx == ry:
            return

        if self.parents[rx] > self.parents[ry]:
            x, y, rx, ry, w = y, x, ry, rx, -w

        self.parents[rx] += self.parents[ry]
        self.parents[ry] = rx
        self.weight[ry] = self.weight[x] - self.weight[y] - w

    def same(self, x, y):
        return self.find(x) == self.find(y)

    def diff(self, x, y):
        return self.weight[x] - self.weight[y]


def main():
    N, M, *LRD = list(map(int, read().split()))

    uf = UnionFindWeighted(N)
    for l, r, d in zip(*[iter(LRD)] * 3):
        l -= 1
        r -= 1
        if uf.same(l, r) and uf.diff(l, r) != d:
            print('No')
            return
        else:
            uf.union(l, r, d)

    print('Yes')
    return


if __name__ == '__main__':
    main()