I would do it like that:
1)Let's use backtracking with some heuristics(I don't know how fast it would actually work).
2)Let's assume that the the current state is S(state is defined by the tiles which are left).
If no tiles are left, the solution is found.
Otherwise, you can use, let's say, depth first search to find the pairs of matching tiles.
A naive solution would be to try to match every pair, remove it and keep searching(and do backtracking if this branch fails).
However, there are a few heuristic to speed up the search:
a)If there are only two tiles of one type and they can be removed, remove them. Do not try to remove any other pairs in this state. I claim that if solution exists, it can obtained by removing this pair first.
b)If all tiles of one type can be matched now(even if there are more than 2 of them), match them. Do not try to remove any other pairs in this state.
c)If neither a) nor b) applies, then you will have to try all possibilities(like in a naive version).
As you can see, these heuristics allow you to avoid branching if either a) or b) applies to the current state, so they can speed up the search(especially at the end of the game, when only a few tiles are left and almost all of them are connected).
P.S You can also use memoization to avoid visiting the same state twice.