You're almost there...
SELECT z.ZipCode, z.CountyName,
MAX(CASE WHEN productid = 1 THEN customerid end) AS 'product1',
MAX(CASE WHEN productid = 2 THEN customerid end) AS 'product2'
FROM @Coverage c
INNER JOIN @Zips z ON
GROUP BY z.ZipCode, z.CountyName
When you say SELECT DISTINCT... it returns the distinct combinations of all columns, including the case statements. Using GROUP BY with the MAX() aggregation functions, you get only 1 row for each zip/county combination and the highest customerid for that combination.
By the way, I'm not quite sure what customerID has to do with anything. I'm taking you at your word that it produces the results you want. Usually, I take counts with queries like this using this format for the case statements:
sum(CASE WHEN productid = 1 then 1 else 0 end) as product1,
sum(CASE WHEN productid = 2 then 1 else 0 end) as product2,
Against stupidity the gods themselves contend in vain. -- Friedrich Schiller
Stop, children, what's that sound? Everybody look what's going down. -- Stephen Stills