Пример #1
0
        /// <summary>
        /// Initializes a new instance of the <see cref="ResultBase{TResultType}"/> class.
        /// </summary>
        /// <param name="runtime">
        /// The observed runtime.
        /// </param>
        /// <param name="targetAlgorithmStatus">
        /// The target algorithm status.
        /// </param>
        protected ResultBase(TimeSpan runtime, TargetAlgorithmStatus targetAlgorithmStatus)
        {
            if (targetAlgorithmStatus == TargetAlgorithmStatus.Running)
            {
                throw new ArgumentOutOfRangeException(
                          nameof(targetAlgorithmStatus),
                          "While creating a result, the target algorithm status should not be running.");
            }

            this.Runtime = runtime;
            this.TargetAlgorithmStatus = targetAlgorithmStatus;
        }
Пример #2
0
        /// <summary>
        /// Initializes a new instance of the <see cref="GurobiResult" /> class.
        /// </summary>
        /// <param name="gap">The MIP gap at the end of the run.</param>
        /// <param name="runtime">The runtime in milliseconds.</param>
        /// <param name="targetAlgorithmStatus">The target algorithm status.</param>
        /// <param name="hasValidSolution">Whether a valid solution was found.</param>
        public GurobiResult(double gap, TimeSpan runtime, TargetAlgorithmStatus targetAlgorithmStatus, bool hasValidSolution)
            : base(runtime, targetAlgorithmStatus)
        {
            // Check some parameters.
            if (gap < 0)
            {
                throw new ArgumentOutOfRangeException($"Gap has to be nonnegative, but is {gap}.");
            }

            // Set them.
            this.Gap              = gap;
            this.Runtime          = runtime;
            this.HasValidSolution = hasValidSolution;
        }
Пример #3
0
        /// <summary>
        /// Creates a <see cref="ResultBase{TResultType}"/> that represents a cancelled run.
        /// </summary>
        /// <param name="runtime">
        /// Run's duration before cancellation.
        /// </param>
        /// <param name="targetAlgorithmStatus">The final <see cref="TargetAlgorithmStatus"/>. Default is TargetAlgorithmStatus.CancelledByTimeout.</param>
        /// <returns>
        /// A <see cref="ResultBase{TResultType}"/> representing a cancelled run.
        /// </returns>
        public static TResultType CreateCancelledResult(
            TimeSpan runtime,
            TargetAlgorithmStatus targetAlgorithmStatus = TargetAlgorithmStatus.CancelledByTimeout)
        {
            if (targetAlgorithmStatus == TargetAlgorithmStatus.Running || targetAlgorithmStatus == TargetAlgorithmStatus.Finished)
            {
                throw new ArgumentOutOfRangeException(
                          nameof(targetAlgorithmStatus),
                          "While creating a cancelled result, the target algorithm status should not be running or finished.");
            }

            return(new TResultType()
            {
                TargetAlgorithmStatus = targetAlgorithmStatus, Runtime = runtime
            });
        }
Пример #4
0
 /// <summary>
 /// Initializes a new instance of the <see cref="AdapterDataRecord{TResult}"/> class.
 /// </summary>
 /// <param name="targetAlgorithmName">The target algorithm name.</param>
 /// <param name="targetAlgorithmStatus">The target algorithm status.</param>
 /// <param name="expendedCpuTime">The expended cpu time.</param>
 /// <param name="expendedWallClockTime">The expended wall clock time.</param>
 /// <param name="timeStamp">The time stamp.</param>
 /// <param name="adapterFeaturesHeader">The adapter features header.</param>
 /// <param name="adapterFeatures">The adapter features.</param>
 /// <param name="currentGrayBoxResult">The current gray box result.</param>
 public AdapterDataRecord(
     string targetAlgorithmName,
     TargetAlgorithmStatus targetAlgorithmStatus,
     TimeSpan expendedCpuTime,
     TimeSpan expendedWallClockTime,
     DateTime timeStamp,
     string[] adapterFeaturesHeader,
     double[] adapterFeatures,
     TResult currentGrayBoxResult)
 {
     this.TargetAlgorithmName   = targetAlgorithmName;
     this.TargetAlgorithmStatus = targetAlgorithmStatus;
     this.ExpendedCpuTime       = expendedCpuTime;
     this.ExpendedWallClockTime = expendedWallClockTime;
     this.TimeStamp             = timeStamp;
     this.AdapterFeaturesHeader = adapterFeaturesHeader;
     this.AdapterFeatures       = adapterFeatures;
     this.CurrentGrayBoxResult  = currentGrayBoxResult;
 }
Пример #5
0
 /// <summary>
 /// Initializes a new instance of the <see cref="ContinuousResult" /> class.
 /// </summary>
 /// <param name="value">The value it should hold.</param>
 /// <param name="runtime">The runtime.</param>
 /// <param name="targetAlgorithmStatus">The <see cref="TargetAlgorithmStatus"/>.</param>
 public ContinuousResult(double value, TimeSpan runtime, TargetAlgorithmStatus targetAlgorithmStatus = TargetAlgorithmStatus.Finished)
     : base(runtime, targetAlgorithmStatus)
 {
     this.Value = value;
 }
Пример #6
0
 public void CreateCancelledResultThrowsIfTargetAlgorithmStatusIsRunningOrFinished(TargetAlgorithmStatus targetAlgorithmStatus)
 {
     Assert.Throws <ArgumentOutOfRangeException>(
         () => { ResultBase <TestResult> .CreateCancelledResult(TimeSpan.FromSeconds(30), targetAlgorithmStatus); });
 }
Пример #7
0
 /// <inheritdoc/>
 public void CancelByGrayBox()
 {
     this._targetAlgorithmStatus = TargetAlgorithmStatus.CancelledByGrayBox;
     this._recordTimer?.Dispose();
     this._innerCancellationTokenSource.Cancel();
 }
Пример #8
0
        /// <summary>
        /// Creates a task that runs Gurobi on the given instance.
        /// </summary>
        /// <param name="instance">
        /// Instance to run on.
        /// </param>
        /// <param name="cancellationToken">
        /// The cancellation token given to the task. NOTE: In this implementation, we ignore this cancellation token, since Gurobi uses its own cancellation token in the callback.
        /// </param>
        /// <returns>
        /// A task that returns the run's runtime, gap, feasibility and completion status onto return.
        /// </returns>
        public Task <GurobiResult> Run(InstanceSeedFile instance, CancellationToken cancellationToken)
        {
            // Check if the runner has already been disposed.
            if (this._hasAlreadyBeenDisposed)
            {
                throw new ObjectDisposedException("GurobiRunner", "Called Run on a disposed GurobiRunner.");
            }

            // Continue if it hasn't.
            // ReSharper disable once MethodSupportsCancellation
            var solveTask = Task.Run(
                () =>
            {
                this._recordTimer = null;
                try
                {
                    // Prepare Gurobi model: Use configured _environment and the given instance,
                    // then add a cancellation token source and the Gurobi callback for cancellation.
                    var instanceFile = new FileInfo(instance.Path);
                    if (!File.Exists(instanceFile.FullName))
                    {
                        throw new FileNotFoundException($"Instance {instanceFile.FullName} not found!");
                    }

                    LoggingHelper.WriteLine(VerbosityLevel.Debug, $"Setting MIPGap to {this._runnerConfiguration.TerminationMipGap}");
                    this._environment.MIPGap = this._runnerConfiguration.TerminationMipGap;
                    LoggingHelper.WriteLine(VerbosityLevel.Debug, $"Current Seed: {instance.Seed}");
                    this._environment.Seed      = instance.Seed;
                    this._environment.TimeLimit = this._runnerConfiguration.CpuTimeout.TotalSeconds;

                    if (!Directory.Exists("GurobiLog"))
                    {
                        Directory.CreateDirectory("GurobiLog");
                    }

                    var instanceFileNameWithoutExtension = GurobiUtils.GetFileNameWithoutGurobiExtension(instanceFile);

                    this._environment.LogFile = "GurobiLog" + Path.DirectorySeparatorChar
                                                + $"GurobiRunner_{DateTime.Now:yy-MM-dd_HH-mm-ss-ffff}_"
                                                + instanceFileNameWithoutExtension + $"_{Guid.NewGuid()}.log";

                    var model = new GRBModel(this._environment, instanceFile.FullName)
                    {
                        ModelName = instanceFileNameWithoutExtension
                    };

                    if (GurobiRunner.TryToGetMstFile(instanceFile.DirectoryName, instanceFileNameWithoutExtension, out var mstFileFullName))
                    {
                        model.Read(mstFileFullName);
                    }

                    this._startTimeStamp        = DateTime.Now;
                    this._targetAlgorithmStatus = TargetAlgorithmStatus.Running;

                    this._innerCancellationTokenSource = new CancellationTokenSource(this._runnerConfiguration.CpuTimeout);

                    this._grbCallback = new GurobiCallback(
                        this._innerCancellationTokenSource.Token,
                        this._tunerConfiguration.EnableDataRecording,
                        this._startTimeStamp);
                    model.SetCallback(this._grbCallback);

                    if (this._tunerConfiguration.EnableDataRecording)
                    {
                        this._lastRuntimeFeatures = null;
                        this.SetGurobiInstanceFeatures(model);

                        // Start record timer.
                        var autoResetEvent = new AutoResetEvent(false);
                        this._recordTimer  = new Timer(
                            (timerCallback) =>
                        {
                            var currentTimeStamp = DateTime.Now;
                            if (currentTimeStamp - this._startTimeStamp < this._runnerConfiguration.CpuTimeout)
                            {
                                // Write current line to data log.
                                var currentAdapterData = this.CreateCurrentAdapterDataRecord(currentTimeStamp);
                                this.OnNewDataRecord?.Invoke(this, currentAdapterData);
                            }
                        },
                            autoResetEvent,
                            TimeSpan.FromSeconds(0),
                            this._tunerConfiguration.DataRecordUpdateInterval);
                    }

                    // Optimize. This step may be aborted in the callback.
                    model.Optimize();

                    if (this._targetAlgorithmStatus != TargetAlgorithmStatus.CancelledByGrayBox)
                    {
                        this._recordTimer?.Dispose();
                        this._targetAlgorithmStatus = this.GetIsRunInterrupted(model)
                                                                  ? TargetAlgorithmStatus.CancelledByTimeout
                                                                  : TargetAlgorithmStatus.Finished;
                    }

                    var finalTimeStamp = DateTime.Now;
                    var result         = this.CreateGurobiResult(finalTimeStamp, model);

                    if (this._tunerConfiguration.EnableDataRecording)
                    {
                        // Write last line to data log.
                        var lastAdapterData = this.CreateFinalAdapterDataRecord(finalTimeStamp, model, result);
                        this.OnNewDataRecord?.Invoke(this, lastAdapterData);
                    }

                    // Before returning, dispose of Gurobi model.
                    model.Dispose();

                    return(result);
                }
                finally
                {
                    this._recordTimer?.Dispose();
                }
            });

            return(solveTask);
        }
Пример #9
0
 /// <summary>
 /// Initializes a new instance of the <see cref="RuntimeResult"/> class.
 /// </summary>
 /// <param name="runtime">The runtime.</param>
 /// <param name="targetAlgorithmStatus">The <see cref="TargetAlgorithmStatus"/>.</param>
 public RuntimeResult(TimeSpan runtime, TargetAlgorithmStatus targetAlgorithmStatus = TargetAlgorithmStatus.Finished)
     : base(runtime, targetAlgorithmStatus)
 {
 }
Пример #10
0
 /// <summary>
 /// Returns the data log file name, which matches the <see cref="DataLogFileNameRegex"/>.
 /// </summary>
 /// <param name="generationId">The generation id.</param>
 /// <param name="processId">The process id.</param>
 /// <param name="actorId">The actor id.</param>
 /// <param name="targetAlgorithmStatus">The target algorithm status.</param>
 /// <returns>The data log file name.</returns>
 public static string GetDataLogFileName(int generationId, int processId, int actorId, TargetAlgorithmStatus targetAlgorithmStatus)
 {
     return($"dataLog_generation_{generationId}_process_{processId}_id_{actorId}_{targetAlgorithmStatus}.csv");
 }