public static string ToText(FileStream binaryFile, out SudokuGridConstraints constraints, out byte[] numbersKinds, out SudokuGridMetrics metrics) { var binary = new byte[binaryFile.Length]; binaryFile.Position = 0; binaryFile.Read(binary, 0, (int)binaryFile.Length); binaryFile.Position = 0; return(ToText(binary, out constraints, out numbersKinds, out metrics)); }
private static string BinaryNonUniformToText(byte[] data, SudokuGridMetrics metrics, ushort zerosPairsPos, byte bitsPerPos, byte bitsPerZerosQuantity, SudokuGridConstraints constraints) { // extraction var numbers = new byte[zerosPairsPos]; Array.Copy(data, 0, numbers, 0, zerosPairsPos); numbers = DecompressNumbers(numbers, metrics.MaximumNumber); if (numbers[numbers.Length - 1] == 0) { var nums = new byte[numbers.Length - 1]; Array.Copy(numbers, 0, nums, 0, nums.Length); numbers = nums; } var zerosPairsCompressed = new byte[data.Length - zerosPairsPos]; Array.Copy(data, zerosPairsPos, zerosPairsCompressed, 0, zerosPairsCompressed.Length); ushort[] zerosPairs = DecompressZerosPairs(zerosPairsCompressed, bitsPerPos, bitsPerZerosQuantity); // combining decompressed sequences var sb = new StringBuilder(metrics.CellsTotal); ushort j; ushort indNumbers = 0; ushort indZerosPairs = 0; for (ushort i = 0; i < metrics.CellsTotal;) { if ((indZerosPairs < zerosPairs.Length) && (i < zerosPairs[indZerosPairs])) // possible numbers are at the beginning { sb.Append(numbers[indNumbers++]); ++i; } else if ((indZerosPairs < zerosPairs.Length) && (i == zerosPairs[indZerosPairs])) // zeros (either at the beginning or later) { indZerosPairs++; for (j = 0; j < zerosPairs[indZerosPairs]; ++j, ++i) { sb.Append("0"); } indZerosPairs++; } else // numbers are at the end { for (j = i; j < metrics.CellsTotal; ++j, ++i) { sb.Append(numbers[indNumbers++]); } } } return(sb.ToString()); }
public static string ToText(byte[] binary, out SudokuGridConstraints constraints, out byte[] numbersKinds, out SudokuGridMetrics metrics) { // !!! temporary !!! numbersKinds = null; var alg = (SudokuConvertionAlgorithm)(binary[0]); byte[] data; switch (alg) { case SudokuConvertionAlgorithm.Uniform: constraints = (SudokuGridConstraints)(binary[1]); metrics = new SudokuGridMetrics(binary[2], binary[3], binary[4]); data = new byte[binary.Length - ((constraints == SudokuGridConstraints.Traditional) ? HEADER_UNIFORM_LENGTH : HEADER_UNIFORM_RESTRICTED_LENGTH)]; Array.Copy(binary, (constraints == SudokuGridConstraints.Traditional) ? HEADER_UNIFORM_LENGTH : HEADER_UNIFORM_RESTRICTED_LENGTH, data, 0, data.Length); return(BinaryUniformToText(data, binary[2], constraints)); case SudokuConvertionAlgorithm.NonUniform: var zerosPairsPos = (ushort)((binary[1] << 8) | binary[2]); var bitsPerPos = (byte)((binary[3] >> 4) + 1); var bitsPerZerosQuantity = (byte)(((byte)(binary[3] << 4) >> 4) + 1); constraints = (SudokuGridConstraints)(binary[4]); metrics = new SudokuGridMetrics(binary[5], binary[6], binary[7]); data = new byte[binary.Length - ((constraints == SudokuGridConstraints.Traditional) ? HEADER_NONUNIFORM_LENGTH : HEADER_NONUNIFORM_RESTRICTED_LENGTH)]; Array.Copy(binary, (constraints == SudokuGridConstraints.Traditional) ? HEADER_NONUNIFORM_LENGTH : HEADER_NONUNIFORM_RESTRICTED_LENGTH, data, 0, data.Length); return(BinaryNonUniformToText(data, metrics, zerosPairsPos, bitsPerPos, bitsPerZerosQuantity, constraints)); default: // dummy code constraints = SudokuGridConstraints.Traditional; metrics = SudokuGridMetrics.Empty; return(null); } }
/// <summary> /// Creates binary file with compressed data. /// </summary> /// <param name="textFile">File with text representation of a grid.</param> /// <param name="outputFilePath">Fully qualified name of output file.</param> /// <param name="alg">Preferable compression algorithm.</param> /// <returns>Seeked to the beginning binary file with read-write acessibilty /// (existing file will be overwritten).</returns> public static FileStream CreateBinaryFromText(FileStream textFile, string outputFilePath, SudokuConvertionAlgorithm alg) { // TODO: ? duplicate functionality -- use ToBinary(FileStream, ...) instead textFile.Position = 0; string content = new StreamReader(textFile).ReadToEnd(); textFile.Position = 0; var restrictions = SudokuGridConstraints.Traditional; var metrics = new SudokuGridMetrics(9, 3, 3); byte[] binary = SudokuConverter.ToBinary(content, alg, restrictions, metrics); var outputFile = new FileStream(outputFilePath, FileMode.Create, FileAccess.ReadWrite); outputFile.Write(binary, 0, binary.Length); outputFile.Position = 0; return(outputFile); }
public static byte[] ToBinary(string content, SudokuConvertionAlgorithm algorithm, SudokuGridConstraints constraints, SudokuGridMetrics metrics) { byte[] compressedContent; byte[] result; switch (algorithm) { case SudokuConvertionAlgorithm.Uniform: compressedContent = TextToBinaryUniform(content, metrics.MaximumNumber); result = new byte[(constraints == SudokuGridConstraints.Traditional) ? HEADER_UNIFORM_LENGTH : HEADER_UNIFORM_RESTRICTED_LENGTH + compressedContent.Length]; //if (constraints == SudokuGridConstraints.Traditional) //{ // result = new byte[HEADER_UNIFORM_LENGTH + compressedContent.Length]; //} //else //{ // result = new byte[HEADER_UNIFORM_RESTRICTED_LENGTH + compressedContent.Length]; //} result[0] = (byte)SudokuConvertionAlgorithm.Uniform; result[1] = (byte)constraints; result[2] = metrics.MaximumNumber; result[3] = metrics.BlockWidth; result[4] = metrics.BlockHeight; if (constraints != SudokuGridConstraints.Traditional) { throw new NotImplementedException(); //var restrictionsPos = (ushort)(); //result[5] = (byte)(); } Array.Copy(compressedContent, 0, result, (constraints == SudokuGridConstraints.Traditional) ? HEADER_UNIFORM_LENGTH : HEADER_UNIFORM_RESTRICTED_LENGTH, compressedContent.Length); return(result); case SudokuConvertionAlgorithm.NonUniform: ushort zerosPairsPos; byte bitsPerPos; byte bitsPerZerosQuantity; compressedContent = TextToBinaryNonUniform(content, metrics.MaximumNumber, out zerosPairsPos, out bitsPerPos, out bitsPerZerosQuantity); result = new byte[(constraints == SudokuGridConstraints.Traditional) ? HEADER_NONUNIFORM_LENGTH : HEADER_NONUNIFORM_RESTRICTED_LENGTH + compressedContent.Length]; result[0] = (byte)SudokuConvertionAlgorithm.NonUniform; result[1] = (byte)(zerosPairsPos >> 8); result[2] = (byte)zerosPairsPos; result[3] = (byte)(((bitsPerPos - 1) << 4) | (bitsPerZerosQuantity - 1)); result[4] = (byte)constraints; result[5] = metrics.MaximumNumber; result[6] = metrics.BlockWidth; result[7] = metrics.BlockHeight; Array.Copy(compressedContent, 0, result, (constraints == SudokuGridConstraints.Traditional) ? HEADER_NONUNIFORM_LENGTH : HEADER_NONUNIFORM_RESTRICTED_LENGTH, compressedContent.Length); //Array.Copy(compressedContent, 0, result, NONLINEAR_HEADER_LENGTH, compressedContent.Length); return(result); default: return(null); } }