public void EditShow() { StructureOfProblem problem = new StructureOfProblem(); problem.ProblemID = 1; problem.QuestionName = "动态规划"; problem.InputSample = "1 7 4 9 2 5\r\n1 2 3 4 5 6 7 8 9"; problem.OutputSample = "6\r\n2"; ProblemList.GetAll().Clear(); ProblemList.Add(problem); ProblemUpdate problemUpdate = new ProblemUpdate(problem.ProblemID); Assert.AreEqual(problemUpdate.QuestionName, problem.QuestionName); Assert.AreEqual(problemUpdate.InputSamples, problem.InputSample); Assert.AreEqual(problemUpdate.OutputSamples, problem.OutputSample); Assert.AreEqual(problemUpdate.QuestionDescription, problem.QuestionDescription); //修改题目名字 string newQuestionName = "贪心"; problemUpdate.QuestionName = newQuestionName; Assert.AreEqual(problemUpdate.QuestionName, newQuestionName); }
/// <summary> /// Get Updates on the work being completed from the WorkerRole that is working on this problem using this strategy as they are happening /// </summary> /// <param name="ctx"><see cref="ZeroMQ.ZmqContext"/> on which to open ZmqSocket.SUB connection to the Publisher WorkerRole doing the work</param> /// <param name="strategy">The <see cref="WaterBucket.Domain.ISolutionStrategy"/> being employed to solve the problem on which you want to receive update messages</param> /// <param name="onCompletion">What to execute when the Worker has sent a completion of the problem message</param> /// <returns>A sequence of <see cref="WaterBucket.Domain.BucketActionStep"/>s every time one is received on the <see cref="ZeroMQ.ZmqSocket"/> from the WorkerRole</returns> /// <seealso cref="ZeroMQ.ZmqSocket"/> protected IEnumerable<BucketActionStep> GetWorkerUpdates(ZmqContext ctx, ISolutionStrategy strategy, Action<SolutionResult> onCompletion = null) { if (ctx == null) throw new ArgumentNullException("ctx"); if (strategy == null) throw new ArgumentNullException("strategy"); var publisherAddresses = GetPublisherAddresses(); if (!publisherAddresses.Any()) { throw new WorkerException("Could not get any publisher endpoints to receive messages from the Worker"); } // Sockets are NOT Thread safe so they must be created in the Thread in which they will be used ZmqSocket subscriber = ctx.CreateSocket(SocketType.SUB); subscriber.Subscribe(Encoding.UTF8.GetBytes(strategy.Signature)); foreach (var pubAddr in publisherAddresses) { subscriber.Connect(pubAddr); } ProblemUpdate update; do { update = null; // This is the blocking version of Receiving from a ZMQ Socket - this is okay since we will run this call from a child Task or wrap in Rx ZmqMessage msg = subscriber.ReceiveMessage(); // Skip the first Frame since it is the Subscription Prefix var msgSig = msg.Unwrap(); // Get the UpdateType from the Message byte[] updateTypeData = msg.Unwrap().Buffer; ProblemUpdateType updateType = (ProblemUpdateType)updateTypeData[0]; //update = new ProblemUpdate(updateType, msg.Last.Buffer); // Find the data demarcation frame var updateFrames = msg.SkipWhile(f => (f.BufferSize != 1) && (f.Buffer[0] != 0x7f));//.ToList(); // Skip the data demarcation frame when creating the ProblemUpdate update = new ProblemUpdate(updateType, updateFrames.Skip(1).ToList()); if (update.IsAction || update.IsInitial) // Return BucketActionSteps to the awaiting caller yield return update.IntoFrameableType<BucketActionStep>().UpdateState; } while ((update != null) && !(update.IsCompletion || update.IsError)); if (update != null) { // Signal Completion if ((update.IsCompletion) && (onCompletion != null)) onCompletion(update.IntoFrameableType<SolutionResult>().UpdateState); // Throw an Exception to the caller if the WorkerRole experienced an Exception if (update.IsError) { throw update.GetException<Exception>(); } } }
public void TestSocketReceive() { // Arrange var ctx = ZmqContext.Create(); var sub = ctx.CreateSocket(SocketType.SUB); Problem testProblem = new Problem(3, 5, 4); byte[] qMsgBytes = new byte[12]; Buffer.BlockCopy(BitConverter.GetBytes(testProblem.FirstBucket.Capacity), 0, qMsgBytes, 0, 4); Buffer.BlockCopy(BitConverter.GetBytes(testProblem.SecondBucket.Capacity), 0, qMsgBytes, 4, 4); Buffer.BlockCopy(BitConverter.GetBytes(testProblem.GoalWaterVolume), 0, qMsgBytes, 8, 4); CloudQueueMessage qMessage = new CloudQueueMessage(qMsgBytes); var smallToBig = new SmallToBigSingleBucketSolutionStrategy(testProblem); var bigToSmall = new BigToSmallSingleBucketSolutionStrategy(testProblem); sub.Connect(_publishAddress); sub.Subscribe(Encoding.UTF8.GetBytes(smallToBig.Signature)); sub.Subscribe(Encoding.UTF8.GetBytes(bigToSmall.Signature)); // Act var subTask = Task.Run(() => { ProblemUpdate update = null; ZmqMessage zqm = sub.ReceiveMessage(TimeSpan.FromSeconds(2)); if (zqm == null) { Assert.Fail("Did not receive a message from the subscription socket within 2 seconds of adding message to Queue"); } int[] numActions = new int[2] { 0, 0 }; bool[] completed = new bool[2] { false, false }; while ((zqm != null) && (!completed.All(c => c))) { zqm = sub.ReceiveMessage(); string msgSig = Encoding.UTF8.GetString(zqm.Unwrap().Buffer); update = new ProblemUpdate(zqm.Select(f => f.Buffer).ToArray()); if (update.IsAction) { if (msgSig.Equals(smallToBig.Signature)) { numActions[SMALL_TO_BIG]++; } else if (msgSig.Equals(bigToSmall.Signature)) { numActions[BIG_TO_SMALL]++; } } else if (update.IsCompletion) { if (msgSig.Equals(smallToBig.Signature)) { completed[SMALL_TO_BIG] = true; } else if (msgSig.Equals(bigToSmall.Signature)) { completed[BIG_TO_SMALL] = true; } } } // Assert Assert.IsFalse(update.IsError, "Received an Exception from the Socket"); Assert.IsTrue(completed.All(c => c), "Not all strategies completed"); Assert.AreEqual(NUM_ACTIONS[SMALL_TO_BIG], numActions[SMALL_TO_BIG], "Small to Big strategy received wrong number of action messages (" + numActions[SMALL_TO_BIG] + ") from socket - expected " + NUM_ACTIONS[SMALL_TO_BIG]); Assert.AreEqual(NUM_ACTIONS[BIG_TO_SMALL], numActions[BIG_TO_SMALL], "Big to Small strategy received wrong number of action messages (" + numActions[BIG_TO_SMALL] + ") from socket - expected " + NUM_ACTIONS[BIG_TO_SMALL]); }); //if ((subTask.Status == TaskStatus.WaitingToRun))// || (subTask.Status == TaskStatus.WaitingForActivation)) // subTask.Start(); _queue.AddMessage(qMessage); subTask.ContinueWith(t => { if (t.IsFaulted) Assert.Fail("subTask threw Exception: " + t.Exception.ToString() + " " + t.Exception.Message); sub.UnsubscribeAll(); sub.Disconnect(_publishAddress); sub.Dispose(); ctx.Dispose(); }); }