#pragma warning (disable:4996)
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <vector>
#include <set>
using namespace std;
typedef pair<int, int> pii;
const int maxn = 1e5 + 5;
vector<pii> opt[2];
int f[maxn];//链的并查集
bool vis[maxn], used[maxn];
int find(int x) {
	return x == f[x] ? x : f[x] = find(f[x]);
}
set<int> Set;
bool val[maxn];
int main() {
	long long nn, mm;
	scanf("%lld%lld", &nn, &mm);
	int q;
	scanf("%d", &q);
	int u, v, x;
	for (int i = 1; i <= q; i++) {
		scanf("%d%d%d", &u, &v, &x);
		opt[x].push_back(make_pair(u, v));
	}
	if (opt[1].size() == 1 && nn == 2) {
		printf("No\n");
		return 0;
	}
	for (auto it : opt[1]) {
		val[it.first] = val[it.second] =  true;
	}
	for (int i = 0; i < nn; i++)f[i] = i;
	for (auto it : opt[0]) {
		if (val[it.first] || val[it.second])continue;
		vis[it.first] = vis[it.second] = true;
		f[find(it.first)] = find(it.second);
	}
	long long sum1 = 0, num = 0;
	for (int i = 0; i < nn; i++)
		if (vis[i]) {
			sum1++;
			if (find(i) == i)
				num++;
		}
	for (auto it : opt[1]) {
		if (vis[it.first] || vis[it.second]) {
			if (vis[it.first])Set.insert(find(it.first));
			if (vis[it.second])Set.insert(find(it.second));
			continue;
		}
		used[it.first] = used[it.second] = true;
	}
	long long num1 = Set.size(), sum2 = 0;
	for (int i = 0; i < nn; i++)
		if (used[i])sum2++;
	long long sum3 = nn - sum1 - sum2;
	//cout << sum1 << ' ' << sum2 << '\n';
	//cout << num << ' ' << num1 << '\n';
	long long m1 = 0;
	if (opt[1].size() == 1 && num1 == 0) {
		m1 = (sum1 + sum2) - (num + 1);
	}
	m1 = sum1 + sum2 - num + num1;
	long long m2 = 0;
	m2 = (num1 + sum2 + sum3) * (num1 + sum2 + sum3 - 1) / 2 + sum1 - num;
	//cout << m1 << ' ' << m2 << '\n';
	if (mm >= m1 && mm <= m2) {
		printf("Yes\n");
	}
	else printf("No\n");

}
