/* Copyright (c) Microsoft Corporation All rights reserved. Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 THIS CODE IS PROVIDED *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABLITY OR NON-INFRINGEMENT. See the Apache Version 2.0 License for specific language governing permissions and limitations under the License. */ using System; using System.Collections; using System.Collections.Generic; using System.IO; using System.Globalization; using System.Reflection; using System.Linq; using Microsoft.Research.DryadLinq.Internal; namespace Microsoft.Research.DryadLinq { interface IForkValue { bool HasValue { get; } object Value { get; } } /// /// Represents an element that may not have valid value. /// /// The element type [Serializable] public struct ForkValue : IForkValue, IEquatable> { private T m_x; private bool m_hasX; /// /// Initializes an instance of ForkValue{T}. Its element has valid value. /// /// The value of the element public ForkValue(T x) { this.m_x = x; this.m_hasX = true; } /// /// true iff the value of the element is valid. /// public bool HasValue { get { return this.m_hasX; } } object IForkValue.Value { get { return this.m_x; } } /// /// Gets the value of the element. It is valid only if HasValue returns true. /// public T Value { get { return this.m_x; } set { this.m_x = value; this.m_hasX = true; } } /// /// Gets the hash code of this instance of ForkValue. /// /// An integer hash code public override int GetHashCode() { if (!this.HasValue) { return 0; } return this.Value.GetHashCode(); } /// /// Determines whether the current ForkValue is equal to a specified ForkValue /// /// A specified ForkValue /// true iff the current ForkValue is equal to the argument public bool Equals(ForkValue fval) { if (!this.HasValue) { return !fval.HasValue; } return fval.HasValue && this.Value.Equals(fval.Value); } } /// /// Represents a pair of elements that may not have valid values. /// /// The type of the first element /// The type of the second element [Serializable] public struct ForkTuple : IEquatable> { private T1 m_x; private T2 m_y; private bool m_hasX; private bool m_hasY; /// /// Initializes an instnace of ForkTuple of two elements. Both elements have valid values. /// /// The first element /// The second element public ForkTuple(T1 x, T2 y) { this.m_x = x; this.m_y = y; this.m_hasX = true; this.m_hasY = true; } /// /// true iff the value of the first element is valid. /// public bool HasFirst { get { return this.m_hasX; } } /// /// true ifff the value of the second element is valid. /// public bool HasSecond { get { return this.m_hasY; } } /// /// Gets and sets the first element. /// public T1 First { get { return this.m_x; } set { this.m_x = value; this.m_hasX = true; } } /// /// Gets and sets the second element. /// public T2 Second { get { return this.m_y; } set { this.m_y = value; this.m_hasY = true; } } /// /// Gets the hash code of this instance of ForkTuple. /// /// An integer hash code public override int GetHashCode() { int hashCode = 0; if (this.HasFirst) { hashCode = (-1521134295 * hashCode) + this.First.GetHashCode(); } if (this.HasSecond) { hashCode = (-1521134295 * hashCode) + this.Second.GetHashCode(); } return hashCode; } /// /// Determines whether the current ForkTuple is equal to a specified ForkTuple. /// /// A specified ForkTuple /// true iff the current ForkTuple is equal to the argument public bool Equals(ForkTuple fval) { if (this.HasFirst) { if (!fval.HasFirst || !this.First.Equals(fval.First)) { return false; } } else { if (fval.HasFirst) return false; } if (this.HasSecond) { if (!fval.HasSecond || !this.Second.Equals(fval.Second)) { return false; } } else { if (fval.HasSecond) return false; } return true; } } /// /// Represents a tuple of three elements that may not have valid values. /// /// The type of the first element /// The type of the second element /// The type of the third element [Serializable] public struct ForkTuple : IEquatable> { private T1 m_x; private T2 m_y; private T3 m_z; private bool m_hasX; private bool m_hasY; private bool m_hasZ; /// /// Initializes an instance of ForkTuple of three elements. All the elements have valid values. /// /// The first element /// The second element /// The third element public ForkTuple(T1 x, T2 y, T3 z) { this.m_x = x; this.m_y = y; this.m_z = z; this.m_hasX = true; this.m_hasY = true; this.m_hasZ = true; } /// /// true iff the value of the first element is valid. /// public bool HasFirst { get { return this.m_hasX; } } /// /// true iff the value of the second element is valid. /// public bool HasSecond { get { return this.m_hasY; } } /// /// true iff the value of the third element is valid. /// public bool HasThird { get { return this.m_hasZ; } } /// /// Gets and sets the first element. /// public T1 First { get { return this.m_x; } set { this.m_x = value; this.m_hasX = true; } } /// /// Gets and sets the second element. /// public T2 Second { get { return this.m_y; } set { this.m_y = value; this.m_hasY = true; } } /// /// Gets and sets the third element. /// public T3 Third { get { return this.m_z; } set { this.m_z = value; this.m_hasZ = true; } } /// /// Gets the hash code of this instance of ForkTuple. /// /// An integer hash code public override int GetHashCode() { int hashCode = 0; if (this.HasFirst) { hashCode = (-1521134295 * hashCode) + this.First.GetHashCode(); } if (this.HasSecond) { hashCode = (-1521134295 * hashCode) + this.Second.GetHashCode(); } if (this.HasThird) { hashCode = (-1521134295 * hashCode) + this.Third.GetHashCode(); } return hashCode; } /// /// Determines whether the current ForkTuple is equal to a specified ForkTuple. /// /// A specified ForkTuple /// true iff the current ForkTuple is equal to the argument public bool Equals(ForkTuple fval) { if (this.HasFirst) { if (!fval.HasFirst || !this.First.Equals(fval.First)) { return false; } } else { if (fval.HasFirst) return false; } if (this.HasSecond) { if (!fval.HasSecond || !this.Second.Equals(fval.Second)) { return false; } } else { if (fval.HasSecond) return false; } if (this.HasThird) { if (!fval.HasThird || !this.Third.Equals(fval.Third)) { return false; } } else { if (fval.HasThird) return false; } return true; } } }