/// <summary> /// Print list of ID/multiplicity pairs. /// </summary> /// <param name="list">List of ID/multiplicity pairs</param> public static void Print(IDMultisetItemList list) { for (int i = 0; i < list.Count; i++) { Console.WriteLine("{0,10:D}{1,5:D}", list[i].Key, list[i].Value); } }
/// <summary> /// Insert ID/multiplicity pair in sorted list /// </summary> /// <param name="item">ID/multiplicity pair to insert in list</param> /// <param name="list">list of ID/multiplicity pairs, sort by multiplicity, largest to smallest</param> static void InsertInOrder(IDMultisetItem item, IDMultisetItemList list) { if (list.Count == 0) { list.Insert(0, item); } else { int i; for (i = 0; i < list.Count; i++) { if (item.Value >= list[i].Value) { break; } } list.Insert(i, item); // inserts ahead of list[i], results in descending order } }
/// <summary> /// Return sorted list of most numerous items in Multiset. /// </summary> /// <param name="multiset">Multiset of IDs</param> /// <param name="maxItems">Maximum number of Multiset items to return</param> /// <returns>List of ID/multiplicity pairs, sorted in order of decreasing multiplicity</returns> public static IDMultisetItemList MostNumerous(IEnumerable<IDMultisetItem> multiset, int maxItems) { // mostNumerous is sorted by item value, mostNumerous[0] is smallest var mostNumerous = new IDMultisetItemList(); foreach (IDMultisetItem item in multiset) { if (mostNumerous.Count < maxItems) { InsertInOrder(item, mostNumerous); } else { int lastIndex = mostNumerous.Count - 1; if (item.Value > mostNumerous[lastIndex].Value) // smallest value is at the end { mostNumerous.RemoveAt(lastIndex); InsertInOrder(item, mostNumerous); } } } return mostNumerous; }
/// <summary> /// Return sorted list of most numerous items in Multiset. /// </summary> /// <param name="multiset">Multiset of IDs</param> /// <param name="maxItems">Maximum number of Multiset items to return</param> /// <returns>List of ID/multiplicity pairs, sorted in order of decreasing multiplicity</returns> public static IDMultisetItemList MostNumerous(IEnumerable <IDMultisetItem> multiset, int maxItems) { // mostNumerous is sorted by item value, mostNumerous[0] is smallest var mostNumerous = new IDMultisetItemList(); foreach (IDMultisetItem item in multiset) { if (mostNumerous.Count < maxItems) { InsertInOrder(item, mostNumerous); } else { int lastIndex = mostNumerous.Count - 1; if (item.Value > mostNumerous[lastIndex].Value) // smallest value is at the end { mostNumerous.RemoveAt(lastIndex); InsertInOrder(item, mostNumerous); } } } return(mostNumerous); }
/// <summary> /// Usage: SocialNework subscriberCount maxFriends /// Both arguments are optional, defaults are 1000 and 10. /// </summary> static void Main(string[] args) { Console.WriteLine("Social Network Sample\n"); #if DEBUG Console.WriteLine("For most accurate timing results, use Release build.\n"); #endif Random random = new Random(1); // seed for random but reproducible runs // Defaults for data generation, may override some on command line int subscriberCount = 10000; int maxFriends = 2000; // Defaults for printed table of results const int maxRows = 16; const int maxCols = 8; const int maxCandidates = maxRows; // Optionally override some defaults on command line if (args.Length > 0) subscriberCount = Int32.Parse(args[0], CultureInfo.CurrentCulture); if (args.Length > 1) maxFriends = Int32.Parse(args[1], CultureInfo.CurrentCulture); Console.WriteLine("Creating data..."); // Allocate subscribers, assign friends for timing tests SubscriberRepository subscribers = new SubscriberRepository(subscriberCount); subscribers.AssignRandomFriends(maxFriends, random); // Print a few subscribers and a summary Console.WriteLine(); Console.WriteLine("Some subscribers and some of their friends"); subscribers.Print(maxRows, maxCols); Console.WriteLine(); Console.WriteLine("{0} subscribers in all, with up to {1} friends or even more ", subscriberCount, maxFriends); // Choose a subscriber seeking friends const SubscriberID id = 0; var subscriber = subscribers.GetSubscriber(id); Console.WriteLine(); Console.WriteLine("Find potential friends for this subscriber, with these friends:"); Console.Write("{0,10:D}", id); subscriber.Print(subscriber.Friends.Count); Console.WriteLine(); // Sequential for var candidates = new IDMultisetItemList(); // to sort, must use list of Multiset items not Multiset itself SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsSequential(id, maxCandidates); return candidates.Count; }, " Sequential for"); Console.WriteLine(); int rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine(); // Parallel.ForEach SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsParallel(id, maxCandidates); return candidates.Count; }, "Parallel.ForEach"); Console.WriteLine(); rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine(); // Sequential LINQ SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsLinq(id, maxCandidates); return candidates.Count; }, " Sequential LINQ"); Console.WriteLine(); rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine(); // PLINQ SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsPLinq(id, maxCandidates); return candidates.Count; }, " PLINQ"); Console.WriteLine(); rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine("\nRun complete... press enter to finish."); Console.ReadLine(); }
/// <summary> /// Insert ID/multiplicity pair in sorted list /// </summary> /// <param name="item">ID/multiplicity pair to insert in list</param> /// <param name="list">list of ID/multiplicity pairs, sort by multiplicity, largest to smallest</param> static void InsertInOrder(IDMultisetItem item, IDMultisetItemList list) { if (list.Count == 0) { list.Insert(0, item); } else { int i; for (i = 0; i < list.Count; i++) { if (item.Value >= list[i].Value) break; } list.Insert(i, item); // inserts ahead of list[i], results in descending order } }
/// <summary> /// Usage: SocialNework subscriberCount maxFriends /// Both arguments are optional, defaults are 1000 and 10. /// </summary> static void Main(string[] args) { Console.WriteLine("Social Network Sample\n"); #if DEBUG Console.WriteLine("For most accurate timing results, use Release build.\n"); #endif Random random = new Random(1); // seed for random but reproducible runs // Defaults for data generation, may override some on command line int subscriberCount = 10000; int maxFriends = 2000; // Defaults for printed table of results const int maxRows = 16; const int maxCols = 8; const int maxCandidates = maxRows; // Optionally override some defaults on command line if (args.Length > 0) { subscriberCount = Int32.Parse(args[0], CultureInfo.CurrentCulture); } if (args.Length > 1) { maxFriends = Int32.Parse(args[1], CultureInfo.CurrentCulture); } Console.WriteLine("Creating data..."); // Allocate subscribers, assign friends for timing tests SubscriberRepository subscribers = new SubscriberRepository(subscriberCount); subscribers.AssignRandomFriends(maxFriends, random); // Print a few subscribers and a summary Console.WriteLine(); Console.WriteLine("Some subscribers and some of their friends"); subscribers.Print(maxRows, maxCols); Console.WriteLine(); Console.WriteLine("{0} subscribers in all, with up to {1} friends or even more ", subscriberCount, maxFriends); // Choose a subscriber seeking friends const SubscriberID id = 0; var subscriber = subscribers.GetSubscriber(id); Console.WriteLine(); Console.WriteLine("Find potential friends for this subscriber, with these friends:"); Console.Write("{0,10:D}", id); subscriber.Print(subscriber.Friends.Count); Console.WriteLine(); // Sequential for var candidates = new IDMultisetItemList(); // to sort, must use list of Multiset items not Multiset itself SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsSequential(id, maxCandidates); return(candidates.Count); }, " Sequential for"); Console.WriteLine(); int rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine(); // Parallel.ForEach SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsParallel(id, maxCandidates); return(candidates.Count); }, "Parallel.ForEach"); Console.WriteLine(); rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine(); // Sequential LINQ SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsLinq(id, maxCandidates); return(candidates.Count); }, " Sequential LINQ"); Console.WriteLine(); rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine(); // PLINQ SampleUtilities.TimedRun(() => { candidates = subscribers.PotentialFriendsPLinq(id, maxCandidates); return(candidates.Count); }, " PLINQ"); Console.WriteLine(); rows = Math.Min(maxRows, candidates.Count); Console.WriteLine("{0} potential friends for this subscriber, and the number of mutual friends", rows); Multiset.Print(candidates); Console.WriteLine("\nRun complete... press enter to finish."); Console.ReadLine(); }