public void Dispose() { switch (operation) { case Operation.Loading: FARLogger.Debug("ConfigAdapter finished loading"); FARConfig.IsLoading = false; Instance.loading = false; break; case Operation.Saving: FARLogger.Debug("ConfigAdapter finished saving"); Instance.saving = false; break; case Operation.None: FARLogger.Debug("ConfigAdapter finished task"); break; default: throw new ArgumentOutOfRangeException(nameof(operation), operation, null); } Instance.Completed = !(Instance.saving || Instance.loading); }
public IEnumerator LoadAsync() { FARLogger.Debug(string.Format("Loading asset bundle {0}", BundlePath)); var createRequest = AssetBundle.LoadFromFileAsync(BundlePath); yield return(createRequest); assetBundle = createRequest.assetBundle; if (assetBundle == null) { FARLogger.Error(string.Format("Could not load asset bundle from {0}", BundlePath)); yield break; } var loadRequest = assetBundle.LoadAllAssetsAsync(typeof(T)); yield return(loadRequest); foreach (var asset in loadRequest.allAssets) { FARLogger.Debug(string.Format("Adding {0} to dictionary", asset)); Add(asset.name, (T)asset); } FARLogger.Debug(string.Format("Finished loading {0} assets from {1}", typeof(T), BundlePath)); AssetsLoaded = true; OnLoad(); }
private IEnumerator DoLoad(Action callback) { // offload to another thread and wait for it to complete Task task = Task.Factory.StartNew(InitTask); yield return(new WaitUntil(() => task.IsCompleted)); if (task.Exception != null) { FARLogger.Exception(task.Exception, "Exception while loading FAR addons:"); yield break; } // do instantiation in the main thread in case any of the types are Unity objects FARLogger.Debug("Instantiating FAR addons"); foreach (Pair <FARAddonAttribute, Type> pair in AddonTypes) { yield return(SetupType(pair.Second, pair.First.Persistant, AddonObjects)); yield return(null); } FARLogger.Debug("Instantiating Reloadable types"); foreach (Type type in ReloadableTypes) { yield return(SetupType(type, true, ReloadableObjects)); yield return(null); } callback?.Invoke(); }
public IEnumerator LoadAsync() { FARLogger.Debug($"Loading asset bundle {BundlePath}"); AssetBundleCreateRequest createRequest = AssetBundle.LoadFromFileAsync(BundlePath); yield return(createRequest); assetBundle = createRequest.assetBundle; if (assetBundle == null) { FARLogger.Error($"Could not load asset bundle from {BundlePath}"); yield break; } AssetBundleRequest loadRequest = assetBundle.LoadAllAssetsAsync(typeof(T)); yield return(loadRequest); foreach (Object asset in loadRequest.allAssets) { FARLogger.Debug($"Adding {asset} to dictionary"); Add(asset.name, (T)asset); } FARLogger.Debug($"Finished loading {typeof(T)} assets from {BundlePath}"); AssetsLoaded = true; OnLoad(); }
public IEnumerator Reload() { FARLogger.Debug("Reloading IReloadable objects"); // sort again in case priorities have changed ReloadableObjects.Sort((x, y) => y.Priority.CompareTo(x.Priority)); foreach (IReloadable reloadable in ReloadableObjects) { reloadable.Completed = false; reloadable.DoReload(); yield return(new WaitUntil(() => reloadable.Completed)); } }
private void Awake() { if (instance == null) { FARLogger.Debug($"MonoSingleton {this} is awake"); instance = this as T; OnAwake(); } else { FARLogger.Trace($"{this} is a MonoSingleton but an instance already exists, destroying self"); destroyingDuplicate = true; Destroy(this); } }
// cannot override default ctor... public LoadGuard(Operation op) { operation = op; switch (op) { case Operation.Loading: FARLogger.Debug("ConfigAdapter started loading"); FARConfig.IsLoading = true; Instance.loading = true; break; case Operation.Saving: FARLogger.Debug("ConfigAdapter started saving"); Instance.saving = true; break; case Operation.None: FARLogger.Debug("ConfigAdapter started task"); break; default: throw new ArgumentOutOfRangeException(nameof(op), op, null); } }
/// <summary> /// C# implementation of /// https://github.com/scipy/scipy/blob/d5617d81064885ef2ec961492bc703f36bb36ee9/scipy/optimize/zeros.py#L95-L363 /// with optional <see cref="minLimit" /> and <see cref="maxLimit" /> constraints for physical problems. The solver /// terminates when it either reaches the maximum number of iterations <see cref="maxIter" />, current and previous /// <see cref="function" /> values are equal, current and previous solutions are close enough, are both NaN or both /// fall outside limits. /// </summary> /// <param name="function">Function to find root of</param> /// <param name="x0">Initial guess</param> /// <param name="x1">Optional second guess</param> /// <param name="tol">Absolute convergence tolerance</param> /// <param name="rTol">Relative convergence tolerance</param> /// <param name="maxIter">Maximum number of iterations</param> /// <param name="maxLimit">Maximum value of the solution</param> /// <param name="minLimit">Minimum value of the solution</param> /// <returns><see cref="OptimizationResult" /> solution</returns> /// <exception cref="ArgumentException">When initial and second guesses are equal</exception> public static OptimizationResult Secant( Func <double, double> function, double x0, double?x1 = null, double tol = 0.001, double rTol = 0.001, int maxIter = 50, double maxLimit = double.PositiveInfinity, double minLimit = double.NegativeInfinity ) { // ReSharper disable CompareOfFloatsByEqualityOperator int funcCalls = 0; double p0 = x0; double p1; if (x1 is null) { const double eps = 1e-4; p1 = x0 * (1 + eps); p1 += p1 >= 0 ? eps : -eps; } else { if (x1 == x0) { throw new ArgumentException($"{nameof(x1)} and {nameof(x0)} must be different"); } p1 = (double)x1; } double q0 = function(p0); double q1 = function(p1); funcCalls += 2; double p = 0; if (Math.Abs(q1) < Math.Abs(q0)) { Swap(ref p0, ref p1); Swap(ref q0, ref q1); } for (int itr = 0; itr < maxIter; itr++) { if (q1 == q0) { if (p1 != p0) { FARLogger.Warning($"Tolerance of {(p1 - p0).ToString(CultureInfo.InvariantCulture)} reached"); } FARLogger.Debug($"Secant method converged in {funcCalls.ToString()} function calls"); return(new OptimizationResult((p1 + p0) / 2, funcCalls, true)); } if (Math.Abs(q1) > Math.Abs(q0)) { p = (-q0 / q1 * p1 + p0) / (1 - q0 / q1); } else { p = (-q1 / q0 * p0 + p1) / (1 - q1 / q0); } if (IsClose(p, p1, tol, rTol)) { FARLogger.Debug($"Secant method converged in {funcCalls.ToString()} function calls with tolerance of {(p1 - p).ToString(CultureInfo.InvariantCulture)}"); return(new OptimizationResult(p, funcCalls, true)); } p0 = p1; q0 = q1; p1 = p; if (double.IsNaN(p0) && double.IsNaN(p1)) { FARLogger.Warning($"Both {nameof(p0)} and {nameof(p1)} are NaN, used {funcCalls.ToString()} function calls"); return(new OptimizationResult(p, funcCalls)); } if (p1 < minLimit && p0 < minLimit || p1 > maxLimit && p0 > maxLimit) { FARLogger.Warning($"{nameof(p1)} and {nameof(p0)} are outside the limits, used {funcCalls.ToString()} function calls"); return(new OptimizationResult(p, funcCalls)); } q1 = function(p1); funcCalls++; } FARLogger.Warning($"Secant method failed to converge in {funcCalls.ToString()} function calls"); return(new OptimizationResult(p, funcCalls)); // ReSharper restore CompareOfFloatsByEqualityOperator }
// ReSharper disable once UnusedMember.Global public static OptimizationResult BrentsMethod( Func <double, double> function, double a, double b, double epsilon = 0.001, int maxIter = int.MaxValue ) { double delta = epsilon * 100; double fa = function(a); double fb = function(b); if (fa * fb >= 0) { FARLogger.Debug("Brent's method failed to converge in 2 calls due to invalid brackets"); return(new OptimizationResult(0, 2)); } if (Math.Abs(fa) < Math.Abs(fb)) { double tmp = fa; fa = fb; fb = tmp; tmp = a; a = b; b = tmp; } double c = a, d = a, fc = function(c); int funcCalls = 3; double s = b; bool flag = true; for (int iter = 0; iter < maxIter; iter++) { if (fa - fc > double.Epsilon && fb - fc > double.Epsilon) //inverse quadratic interpolation { s = a * fc * fb / ((fa - fb) * (fa - fc)); s += b * fc * fa / ((fb - fa) * (fb - fc)); s += c * fc * fb / ((fc - fa) * (fc - fb)); } else { s = (b - a) / (fb - fa); //secant method s *= fb; s = b - s; } double b_s = Math.Abs(b - s), b_c = Math.Abs(b - c), c_d = Math.Abs(c - d); //Conditions for bisection method bool condition1; double a3pb_over4 = (3 * a + b) * 0.25; if (a3pb_over4 > b) { if (s < a3pb_over4 && s > b) { condition1 = false; } else { condition1 = true; } } else if (s > a3pb_over4 && s < b) { condition1 = false; } else { condition1 = true; } bool condition2; if (flag && b_s >= b_c * 0.5) { condition2 = true; } else { condition2 = false; } bool condition3; if (!flag && b_s >= c_d * 0.5) { condition3 = true; } else { condition3 = false; } bool condition4; if (flag && b_c <= delta) { condition4 = true; } else { condition4 = false; } bool condition5; if (!flag && c_d <= delta) { condition5 = true; } else { condition5 = false; } if (condition1 || condition2 || condition3 || condition4 || condition5) { s = a + b; s *= 0.5; flag = true; } else { flag = false; } double fs = function(s); funcCalls++; d = c; c = b; if (fa * fs < 0) { b = s; fb = fs; } else { a = s; fa = fs; } if (Math.Abs(fa) < Math.Abs(fb)) { double tmp = fa; fa = fb; fb = tmp; tmp = a; a = b; b = tmp; } if (fs.NearlyEqual(0) || Math.Abs(a - b) <= epsilon) { return(new OptimizationResult(s, funcCalls, true)); } } FARLogger.Debug($"Brent's method failed to converged in {funcCalls.ToString()} function calls"); return(new OptimizationResult(s, funcCalls)); }