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

using VI = vector<int>;
using VVI = vector<VI>;
using PII = pair<int, int>;
using LL = long long;
using VL = vector<LL>;
using VVL = vector<VL>;
using PLL = pair<LL, LL>;
using VS = vector<string>;

#define ALL(a)  begin((a)),end((a))
#define RALL(a) (a).rbegin(), (a).rend()
#define PB push_back
#define EB emplace_back
#define MP make_pair
#define SZ(a) int((a).size())
#define SORT(c) sort(ALL((c)))
#define RSORT(c) sort(RALL((c)))
#define UNIQ(c) (c).erase(unique(ALL((c))), end((c)))

#define FOR(i,a,b) for(int i=(a);i<(b);++i)
#define REP(i,n)  FOR(i,0,n)

#define FF first
#define SS second

#define DUMP(x) cout<<#x<<":"<<(x)<<endl
template<class S, class T>
istream& operator>>(istream& is, pair<S,T>& p){
  return is >> p.FF >> p.SS;
}
template<class T>
istream& operator>>(istream& is, vector<T>& xs){
  for(auto& x: xs)
	is >> x;
  return is;
}
template<class S, class T>
ostream& operator<<(ostream& os, const pair<S,T>& p){
  return os << p.FF << " " << p.SS;
}
template<class T>
ostream& operator<<(ostream& os, const vector<T>& xs){
  for(unsigned int i=0;i<xs.size();++i)
	os << (i?" ":"") << xs[i];
  return os;
}
template<class T>
void maxi(T& x, T y){
  if(x < y) x = y;
}
template<class T>
void mini(T& x, T y){
  if(x > y) x = y;
}


const double EPS = 1e-10;
const double PI  = acos(-1.0);
const LL MOD = 1e9+7;

struct EdgeC{
  int to, cap, cost, rev;
  EdgeC(int to_=0, int cap_ = 0, int cost_ = 0, int rev_ = 0)
	:to(to_), cap(cap_), cost(cost_), rev(rev_){}
};
using GraphC = vector<vector<EdgeC>>;
const int INF = 1e9;

void add_edge(GraphC& G, int from, int to, int cap, int cost){
  G[from].emplace_back(to, cap, cost, G[to].size());
  G[to].emplace_back(from, 0, -cost, G[from].size()-1);
}
int min_cost_flow(GraphC& G, int s, int t, int f){
  int V = G.size();
  vector<int> dist(V);
  vector<int> prevv(V), preve(V);
  int res = 0;
  
  while(f > 0){
	fill(begin(dist), end(dist), INF);
	dist[s] = 0;
	bool update = true;
	while(update){
	  update = false;
	  for(int v=0;v<V;++v){
		if(dist[v] == INF) continue;
		for(unsigned int i=0;i<G[v].size();++i){
		  auto& e = G[v][i];
		  if(e.cap > 0 && dist[v] + e.cost < dist[e.to]){
			dist[e.to] = dist[v] + e.cost;
			prevv[e.to] = v;
			preve[e.to] = i;
			update = true;
		  }
		}
	  }
	}
	if(dist[t] == INF) return -INF;

	int d = f;
	for(int v=t;v!=s;v=prevv[v])
	  d = min(d, G[prevv[v]][preve[v]].cap);

	f -= d;
	res += d * dist[t];
	for(int v=t;v!=s;v=prevv[v]){
	  auto& e = G[prevv[v]][preve[v]];
	  e.cap -= d;
	  G[v][e.rev].cap += d;
	}
  }
  
  return res;
}

int main(){
  cin.tie(0);
  ios_base::sync_with_stdio(false);

  int N, M, L;
  while(cin>>N>>M>>L,N){
	VVI dist(N, VI(N,1e9));
	REP(i,N) dist[i][i] = 0;
	REP(i,M){
	  int u, v, d;
	  cin >> u >> v >> d;
	  mini(dist[u][v], d);
	  mini(dist[v][u], d);
	}
	REP(k,N) REP(i,N) REP(j,N)
	  mini(dist[i][j], dist[i][k] + dist[k][j]);

	vector<PII> qs(L);
	REP(i,L){
	  cin >> qs[i].SS >> qs[i].FF;
	}
	SORT(qs);

	int S = L+L, T = S+1;
	GraphC G(L+L+2);
	REP(i1,L) FOR(i2,i1+1,L){
	  if(qs[i1].FF + dist[qs[i1].SS][qs[i2].SS] <= qs[i2].FF){
		add_edge(G, i1*2+1, i2*2, INF, 0);
	  }
	}
	REP(i,L){
	  add_edge(G, S, i*2, INF, 0);
	  add_edge(G, i*2+1, T, INF, 0);
	  add_edge(G, i*2, i*2+1, 1, -1);
	  add_edge(G, i*2, i*2+1, INF, 0);
	}

	int sum = 0;
	for(int f=1;;++f){
	  sum += min_cost_flow(G, S, T, 1);
	  if(sum == -L){
		cout << f << endl;
		break;
	  }
	}
  }

  return 0;
}



Measured memory_bytes: 23492