i had a very similar problem couple of years ago. the way i eventually implemented this:
1. store every set as a sorted array of member ids (no 2 ids are the same)
2. for iterating over subsets of a given size N start with the 1st N elements of the original set
3. to get to the next subset you implement a sort of "clockwork" mechanism - take the last (highest id) memeber of your subset and replace it with its neighbour in the superset (the next higher id).
4. if there's no such higher neighbour in the superset, increment the next lower member of the subset, and then set the original highest memeber to be the next one after that.
steps 3 and 4 are recursive.
example result sequence for iterating over all triplets of {1,2,3,4,5}:
{1,2,3} - 3 lowest memebers
{1,2,4} - "increment" 3 to 4
{1,2,5} - 4 to 5
{1,3,4} - couldnt "increment" 5, so incremented 2-->3 and picked then next one as 3rd
{1,3,5} - 4-->5
{1,4,5} - couldnt increment 5 ...
{2,3,4} - couldnt increment 5, couldnt increment 4, incremented 1-->2
{2,3,5}
and so on
its more complex than mark's proposal, but takes up less memory and stack space. its also "restartable" - meaning you can pass any subset into the algo and it will get you the "next" subset.