From fd7d46faf0a91d69ff40a426a268419e35b94e35 Mon Sep 17 00:00:00 2001 From: Genevieve Warren <24882762+gewarren@users.noreply.github.com> Date: Wed, 3 Jun 2026 21:11:58 -0700 Subject: [PATCH 1/2] Reinstate supplemental remarks --- .../cpp/System/String/.ctor/sbyte_ctor1.cpp | 20 ++ .../Overview/BigInteger_Examples.cs | 86 ++++++++ .../Overview/ByteAndHex_Examples.cs | 152 +++++++++++++++ .../Overview/ByteAndHex_Examples2.cs | 43 ++++ .../Overview/Mutability_Examples.cs | 75 +++++++ .../BigInteger/Overview/Project.csproj | 8 + .../Complex/Overview/Program.cs | 1 + .../Complex/Overview/Project.csproj | 8 + .../Complex/Overview/create1.cs | 41 ++++ .../Complex/Overview/customfmt1.cs | 85 ++++++++ .../System.Numerics/Complex/Overview/nan1.cs | 28 +++ .../Complex/Overview/precision1.cs | 35 ++++ .../ListT/Overview/addremoveinsert.fs | 66 +++++++ .../ListT/Overview/listclass.fs | 100 ++++++++++ .../List/Overview/Project.vbproj | 8 + .../List/Overview/module1.vb | 183 ++++++++++++++++++ .../List/Overview/source.vb | 100 ++++++++++ .../Overview/BigInteger_Examples.vb | 86 ++++++++ .../Overview/ByteAndHex_Examples.vb | 154 +++++++++++++++ .../Overview/ByteAndHex_Examples2.vb | 45 +++++ .../Overview/Mutability_Examples.vb | 69 +++++++ .../BigInteger/Overview/Project.vbproj | 8 + .../Complex/Overview/Program.vb | 5 + .../Complex/Overview/Project.vbproj | 8 + .../Complex/Overview/create1.vb | 41 ++++ .../Complex/Overview/customfmt1.vb | 76 ++++++++ .../System.Numerics/Complex/Overview/nan1.vb | 29 +++ .../Complex/Overview/precision1.vb | 35 ++++ xml/Microsoft.Win32/Registry.xml | 34 +++- xml/System.Collections.Generic/HashSet`1.xml | 53 ++++- xml/System.Collections.Generic/List`1.xml | 64 +++++- .../KeyedCollection`2.xml | 20 +- .../ObservableCollection`1.xml | 33 +++- .../BinaryExpression.xml | 71 ++++++- xml/System.Linq.Expressions/Expression.xml | 64 +++++- xml/System.Net.Http/HttpClient.xml | 142 +++++++++++++- xml/System.Net.Http/HttpClientHandler.xml | 12 +- xml/System.Net.Sockets/Socket.xml | 26 ++- xml/System.Net/FtpWebRequest.xml | 12 +- xml/System.Net/HttpListener.xml | 50 ++++- xml/System.Numerics/BigInteger.xml | 121 +++++++++++- xml/System.Numerics/Complex.xml | 95 ++++++++- .../SignedXml.xml | 146 +++++++++++++- .../RSACryptoServiceProvider.xml | 20 +- .../RSAParameters.xml | 45 ++++- xml/System.Security/SecureString.xml | 112 ++++++++++- 46 files changed, 2695 insertions(+), 20 deletions(-) create mode 100644 snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp create mode 100644 snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs create mode 100644 snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs create mode 100644 snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.cs create mode 100644 snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs create mode 100644 snippets/csharp/System.Numerics/BigInteger/Overview/Project.csproj create mode 100644 snippets/csharp/System.Numerics/Complex/Overview/Program.cs create mode 100644 snippets/csharp/System.Numerics/Complex/Overview/Project.csproj create mode 100644 snippets/csharp/System.Numerics/Complex/Overview/create1.cs create mode 100644 snippets/csharp/System.Numerics/Complex/Overview/customfmt1.cs create mode 100644 snippets/csharp/System.Numerics/Complex/Overview/nan1.cs create mode 100644 snippets/csharp/System.Numerics/Complex/Overview/precision1.cs create mode 100644 snippets/fsharp/System.Collections.Generic/ListT/Overview/addremoveinsert.fs create mode 100644 snippets/fsharp/System.Collections.Generic/ListT/Overview/listclass.fs create mode 100644 snippets/visualbasic/System.Collections.Generic/List/Overview/Project.vbproj create mode 100644 snippets/visualbasic/System.Collections.Generic/List/Overview/module1.vb create mode 100644 snippets/visualbasic/System.Collections.Generic/List/Overview/source.vb create mode 100644 snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb create mode 100644 snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb create mode 100644 snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.vb create mode 100644 snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb create mode 100644 snippets/visualbasic/System.Numerics/BigInteger/Overview/Project.vbproj create mode 100644 snippets/visualbasic/System.Numerics/Complex/Overview/Program.vb create mode 100644 snippets/visualbasic/System.Numerics/Complex/Overview/Project.vbproj create mode 100644 snippets/visualbasic/System.Numerics/Complex/Overview/create1.vb create mode 100644 snippets/visualbasic/System.Numerics/Complex/Overview/customfmt1.vb create mode 100644 snippets/visualbasic/System.Numerics/Complex/Overview/nan1.vb create mode 100644 snippets/visualbasic/System.Numerics/Complex/Overview/precision1.vb diff --git a/snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp b/snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp new file mode 100644 index 00000000000..f178c345ffc --- /dev/null +++ b/snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp @@ -0,0 +1,20 @@ +// SByte_Ctor1.cpp : Defines the entry point for the console application. +// + +//#include "stdafx.h" + +// +using namespace System; + +void main() +{ + char chars[] = { 'a', 'b', 'c', 'd', '\x00' }; + + char* charPtr = chars; + String^ value = gcnew String(charPtr); + + Console::WriteLine(value); +} +// The example displays the following output: +// abcd +// diff --git a/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs b/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs new file mode 100644 index 00000000000..57efe9e4e17 --- /dev/null +++ b/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs @@ -0,0 +1,86 @@ +using System; +using System.Numerics; + +public class Example +{ + public static void Main() + { + // + BigInteger bigIntFromDouble = new BigInteger(179032.6541); + Console.WriteLine(bigIntFromDouble); + BigInteger bigIntFromInt64 = new BigInteger(934157136952); + Console.WriteLine(bigIntFromInt64); + // The example displays the following output: + // 179032 + // 934157136952 + // + + Console.WriteLine(); + + // + long longValue = 6315489358112; + BigInteger assignedFromLong = longValue; + Console.WriteLine(assignedFromLong); + // The example displays the following output: + // 6315489358112 + // + + Console.WriteLine(); + Console.WriteLine("Casting:"); + // + BigInteger assignedFromDouble = (BigInteger) 179032.6541; + Console.WriteLine(assignedFromDouble); + BigInteger assignedFromDecimal = (BigInteger) 64312.65m; + Console.WriteLine(assignedFromDecimal); + // The example displays the following output: + // 179032 + // 64312 + // + + Console.WriteLine(); + + // + byte[] byteArray = { 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0}; + BigInteger newBigInt = new BigInteger(byteArray); + Console.WriteLine($"The value of newBigInt is {newBigInt} (or 0x{newBigInt:x})."); + // The example displays the following output: + // The value of newBigInt is 4759477275222530853130 (or 0x102030405060708090a). + // + + Console.WriteLine(); + + // + string positiveString = "91389681247993671255432112000000"; + string negativeString = "-90315837410896312071002088037140000"; + BigInteger posBigInt = 0; + BigInteger negBigInt = 0; + + try { + posBigInt = BigInteger.Parse(positiveString); + Console.WriteLine(posBigInt); + } + catch (FormatException) + { + Console.WriteLine($"Unable to convert the string '{positiveString}' to a BigInteger value."); + } + + if (BigInteger.TryParse(negativeString, out negBigInt)) + Console.WriteLine(negBigInt); + else + Console.WriteLine($"Unable to convert the string '{negativeString}' to a BigInteger value."); + + // The example displays the following output: + // 9.1389681247993671255432112E+31 + // -9.0315837410896312071002088037E+34 + // + + Console.WriteLine(); + + // + BigInteger number = BigInteger.Pow(UInt64.MaxValue, 3); + Console.WriteLine(number); + // The example displays the following output: + // 6277101735386680762814942322444851025767571854389858533375 + // + } +} diff --git a/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs b/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs new file mode 100644 index 00000000000..8d4dd1b6bda --- /dev/null +++ b/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs @@ -0,0 +1,152 @@ +using System; +using System.Globalization; +using System.Numerics; + +public class ByteHexExample +{ + public static void Main() + { + RoundtripBigInteger(); + Console.WriteLine(); + RoundtripInt16(); + Console.WriteLine(); + HandleSignsInByteArray(); + Console.WriteLine(); + RoundtripAmbiguous(); + Console.WriteLine(); + RoundtripWithHex(); + } + + private static void RoundtripBigInteger() + { + Console.WriteLine("Round-trip bytes"); + + // + BigInteger number = BigInteger.Pow(Int64.MaxValue, 2); + Console.WriteLine(number); + + // Write the BigInteger value to a byte array. + byte[] bytes = number.ToByteArray(); + + // Display the byte array. + foreach (byte byteValue in bytes) + Console.Write("0x{0:X2} ", byteValue); + Console.WriteLine(); + + // Restore the BigInteger value from a Byte array. + BigInteger newNumber = new BigInteger(bytes); + Console.WriteLine(newNumber); + // The example displays the following output: + // 8.5070591730234615847396907784E+37 + // 0x01 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0x3F + // + // 8.5070591730234615847396907784E+37 + // + } + + private static void RoundtripInt16() + { + Console.WriteLine(); + Console.WriteLine("Round-trip an Int16 value:"); + // + short originalValue = 30000; + Console.WriteLine(originalValue); + + // Convert the Int16 value to a byte array. + byte[] bytes = BitConverter.GetBytes(originalValue); + + // Display the byte array. + foreach (byte byteValue in bytes) + Console.Write("0x{0} ", byteValue.ToString("X2")); + Console.WriteLine(); + + // Pass byte array to the BigInteger constructor. + BigInteger number = new BigInteger(bytes); + Console.WriteLine(number); + // The example displays the following output: + // 30000 + // 0x30 0x75 + // 30000 + // + } + + private static void HandleSignsInByteArray() + { + // + int negativeNumber = -1000000; + uint positiveNumber = 4293967296; + + byte[] negativeBytes = BitConverter.GetBytes(negativeNumber); + BigInteger negativeBigInt = new BigInteger(negativeBytes); + Console.WriteLine(negativeBigInt.ToString("N0")); + + byte[] tempPosBytes = BitConverter.GetBytes(positiveNumber); + byte[] positiveBytes = new byte[tempPosBytes.Length + 1]; + Array.Copy(tempPosBytes, positiveBytes, tempPosBytes.Length); + BigInteger positiveBigInt = new BigInteger(positiveBytes); + Console.WriteLine(positiveBigInt.ToString("N0")); + // The example displays the following output: + // -1,000,000 + // 4,293,967,296 + // + } + + private static void RoundtripAmbiguous() + { + Console.WriteLine("Round-trip an Ambiguous Value:"); + // + BigInteger positiveValue = 15777216; + BigInteger negativeValue = -1000000; + + Console.WriteLine("Positive value: " + positiveValue.ToString("N0")); + byte[] bytes = positiveValue.ToByteArray(); + + foreach (byte byteValue in bytes) + Console.Write("{0:X2} ", byteValue); + Console.WriteLine(); + positiveValue = new BigInteger(bytes); + Console.WriteLine("Restored positive value: " + positiveValue.ToString("N0")); + + Console.WriteLine(); + + Console.WriteLine("Negative value: " + negativeValue.ToString("N0")); + bytes = negativeValue.ToByteArray(); + foreach (byte byteValue in bytes) + Console.Write("{0:X2} ", byteValue); + Console.WriteLine(); + negativeValue = new BigInteger(bytes); + Console.WriteLine("Restored negative value: " + negativeValue.ToString("N0")); + // The example displays the following output: + // Positive value: 15,777,216 + // C0 BD F0 00 + // Restored positive value: 15,777,216 + // + // Negative value: -1,000,000 + // C0 BD F0 + // Restored negative value: -1,000,000 + // + } + + private static void RoundtripWithHex() + { + // + BigInteger negativeNumber = -1000000; + BigInteger positiveNumber = 15777216; + + string negativeHex = negativeNumber.ToString("X"); + string positiveHex = positiveNumber.ToString("X"); + + BigInteger negativeNumber2, positiveNumber2; + negativeNumber2 = BigInteger.Parse(negativeHex, + NumberStyles.HexNumber); + positiveNumber2 = BigInteger.Parse(positiveHex, + NumberStyles.HexNumber); + + Console.WriteLine($"Converted {negativeNumber:N0} to {negativeHex} back to {negativeNumber2:N0}."); + Console.WriteLine($"Converted {positiveNumber:N0} to {positiveHex} back to {positiveNumber2:N0}."); + // The example displays the following output: + // Converted -1,000,000 to F0BDC0 back to -1,000,000. + // Converted 15,777,216 to 0F0BDC0 back to 15,777,216. + // + } +} diff --git a/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.cs b/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.cs new file mode 100644 index 00000000000..d64472f7df2 --- /dev/null +++ b/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.cs @@ -0,0 +1,43 @@ +// +using System; +using System.Globalization; +using System.Numerics; + +public struct HexValue +{ + public int Sign; + public string Value; +} + +public class ByteHexExample2 +{ + public static void Main() + { + uint positiveNumber = 4039543321; + int negativeNumber = -255423975; + + // Convert the numbers to hex strings. + HexValue hexValue1, hexValue2; + hexValue1.Value = positiveNumber.ToString("X"); + hexValue1.Sign = Math.Sign(positiveNumber); + + hexValue2.Value = Convert.ToString(negativeNumber, 16); + hexValue2.Sign = Math.Sign(negativeNumber); + + // Round-trip the hexadecimal values to BigInteger values. + string hexString; + BigInteger positiveBigInt, negativeBigInt; + + hexString = (hexValue1.Sign == 1 ? "0" : "") + hexValue1.Value; + positiveBigInt = BigInteger.Parse(hexString, NumberStyles.HexNumber); + Console.WriteLine($"Converted {positiveNumber} to {hexValue1.Value} and back to {positiveBigInt}."); + + hexString = (hexValue2.Sign == 1 ? "0" : "") + hexValue2.Value; + negativeBigInt = BigInteger.Parse(hexString, NumberStyles.HexNumber); + Console.WriteLine($"Converted {negativeNumber} to {hexValue2.Value} and back to {negativeBigInt}."); + } +} +// The example displays the following output: +// Converted 4039543321 to F0C68A19 and back to 4039543321. +// Converted -255423975 to f0c68a19 and back to -255423975. +// diff --git a/snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs b/snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs new file mode 100644 index 00000000000..929cde2f07d --- /dev/null +++ b/snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs @@ -0,0 +1,75 @@ +using System; +using System.Diagnostics; +using System.Numerics; + +public class MutabilityEx +{ + public static void Main() + { + ShowSimpleAdd(); + PerformBigIntegerOperation(); + PerformWithIntermediary(); + } + + private static void ShowSimpleAdd() + { + // + BigInteger number = BigInteger.Multiply(Int64.MaxValue, 3); + number++; + Console.WriteLine(number); + // + } + + private static void PerformBigIntegerOperation() + { + Stopwatch sw = Stopwatch.StartNew(); + + // + BigInteger number = Int64.MaxValue ^ 5; + int repetitions = 1000000; + // Perform some repetitive operation 1 million times. + for (int ctr = 0; ctr <= repetitions; ctr++) + { + // Perform some operation. If it fails, exit the loop. + if (!SomeOperationSucceeds()) break; + // The following code executes if the operation succeeds. + number++; + } + // + + sw.Stop(); + Console.WriteLine("Incrementing a BigInteger: " + sw.Elapsed.ToString()); + } + + private static void PerformWithIntermediary() + { + Stopwatch sw = Stopwatch.StartNew(); + + // + BigInteger number = Int64.MaxValue ^ 5; + int repetitions = 1000000; + int actualRepetitions = 0; + // Perform some repetitive operation 1 million times. + for (int ctr = 0; ctr <= repetitions; ctr++) + { + // Perform some operation. If it fails, exit the loop. + if (!SomeOperationSucceeds()) break; + // The following code executes if the operation succeeds. + actualRepetitions++; + } + number += actualRepetitions; + // + + sw.Stop(); + Console.WriteLine("Incrementing a BigInteger: " + sw.Elapsed.ToString()); + } + + private static bool SomeOperationSucceeds() + { + return true; + } +} + +// +// CAPS bug: snippet2 is seen as duplicated, even though it isn't. +// diff --git a/snippets/csharp/System.Numerics/BigInteger/Overview/Project.csproj b/snippets/csharp/System.Numerics/BigInteger/Overview/Project.csproj new file mode 100644 index 00000000000..874c98f3477 --- /dev/null +++ b/snippets/csharp/System.Numerics/BigInteger/Overview/Project.csproj @@ -0,0 +1,8 @@ + + + + Library + net10.0 + + + diff --git a/snippets/csharp/System.Numerics/Complex/Overview/Program.cs b/snippets/csharp/System.Numerics/Complex/Overview/Program.cs new file mode 100644 index 00000000000..99e6662d51b --- /dev/null +++ b/snippets/csharp/System.Numerics/Complex/Overview/Program.cs @@ -0,0 +1 @@ +CustomFormatEx.Run(); diff --git a/snippets/csharp/System.Numerics/Complex/Overview/Project.csproj b/snippets/csharp/System.Numerics/Complex/Overview/Project.csproj new file mode 100644 index 00000000000..f99395b4b2b --- /dev/null +++ b/snippets/csharp/System.Numerics/Complex/Overview/Project.csproj @@ -0,0 +1,8 @@ + + + + Exe + net10.0 + + + diff --git a/snippets/csharp/System.Numerics/Complex/Overview/create1.cs b/snippets/csharp/System.Numerics/Complex/Overview/create1.cs new file mode 100644 index 00000000000..10d20d59111 --- /dev/null +++ b/snippets/csharp/System.Numerics/Complex/Overview/create1.cs @@ -0,0 +1,41 @@ +// +using System; +using System.Numerics; + +public class CreateEx +{ + public static void Run() + { + // Create a complex number by calling its class constructor. + Complex c1 = new Complex(12, 6); + Console.WriteLine(c1); + + // Assign a Double to a complex number. + Complex c2 = 3.14; + Console.WriteLine(c2); + + // Cast a Decimal to a complex number. + Complex c3 = (Complex)12.3m; + Console.WriteLine(c3); + + // Assign the return value of a method to a Complex variable. + Complex c4 = Complex.Pow(Complex.One, -1); + Console.WriteLine(c4); + + // Assign the value returned by an operator to a Complex variable. + Complex c5 = Complex.One + Complex.One; + Console.WriteLine(c5); + + // Instantiate a complex number from its polar coordinates. + Complex c6 = Complex.FromPolarCoordinates(10, .524); + Console.WriteLine(c6); + } +} +// The example displays the following output: +// (12, 6) +// (3.14, 0) +// (12.3, 0) +// (1, 0) +// (2, 0) +// (8.65824721882145, 5.00347430269914) +// diff --git a/snippets/csharp/System.Numerics/Complex/Overview/customfmt1.cs b/snippets/csharp/System.Numerics/Complex/Overview/customfmt1.cs new file mode 100644 index 00000000000..6040075babe --- /dev/null +++ b/snippets/csharp/System.Numerics/Complex/Overview/customfmt1.cs @@ -0,0 +1,85 @@ +// +using System; +using System.Numerics; + +public class ComplexFormatter : IFormatProvider, ICustomFormatter +{ + public object GetFormat(Type formatType) + { + if (formatType == typeof(ICustomFormatter)) + return this; + else + return null; + } + + public string Format(string format, object arg, + IFormatProvider provider) + { + if (arg is Complex c1) + { + // Check if the format string has a precision specifier. + int precision; + string fmtString = string.Empty; + if (format.Length > 1) + { + try + { + precision = int.Parse(format.Substring(1)); + } + catch (FormatException) + { + precision = 0; + } + fmtString = "N" + precision.ToString(); + } + if (format.Substring(0, 1).Equals("I", StringComparison.OrdinalIgnoreCase)) + { + // Determine the sign to display. + char sign = c1.Imaginary < 0 ? '-' : '+'; + // Display the determined sign and the absolute value of the imaginary part. + return c1.Real.ToString(fmtString) + " " + sign + " " + Math.Abs(c1.Imaginary).ToString(fmtString) + "i"; + } + else if (format.Substring(0, 1).Equals("J", StringComparison.OrdinalIgnoreCase)) + { + // Determine the sign to display. + char sign = c1.Imaginary < 0 ? '-' : '+'; + // Display the determined sign and the absolute value of the imaginary part. + return c1.Real.ToString(fmtString) + " " + sign + " " + Math.Abs(c1.Imaginary).ToString(fmtString) + "j"; + } + else + return c1.ToString(format, provider); + } + else + { + if (arg is IFormattable formattable) + return formattable.ToString(format, provider); + else if (arg != null) + return arg.ToString(); + else + return string.Empty; + } + } +} +// + +// +public class CustomFormatEx +{ + public static void Run() + { + Complex c1 = new(12.1, 15.4); + Console.WriteLine($"Formatting with ToString: {c1}"); + Console.WriteLine($"Formatting with ToString(format): {c1:N2}"); + Console.WriteLine($"Custom formatting with I0:\t" + + $" {string.Format(new ComplexFormatter(), "{0:I0}", c1)}"); + Console.WriteLine($"Custom formatting with J3:\t" + + $" {string.Format(new ComplexFormatter(), "{0:J3}", c1)}"); + } +} + +// The example displays the following output: +// Formatting with ToString(): <12.1; 15.4> +// Formatting with ToString(format): <12.10; 15.40> +// Custom formatting with I0: 12 + 15i +// Custom formatting with J3: 12.100 + 15.400j +// diff --git a/snippets/csharp/System.Numerics/Complex/Overview/nan1.cs b/snippets/csharp/System.Numerics/Complex/Overview/nan1.cs new file mode 100644 index 00000000000..c9148522415 --- /dev/null +++ b/snippets/csharp/System.Numerics/Complex/Overview/nan1.cs @@ -0,0 +1,28 @@ +// +using System; +using System.Numerics; + +public class NaNEx +{ + public static void Run() + { + Complex c1 = new Complex(Double.MaxValue / 2, Double.MaxValue / 2); + + Complex c2 = c1 / Complex.Zero; + Console.WriteLine(c2.ToString()); + c2 = c2 * new Complex(1.5, 1.5); + Console.WriteLine(c2.ToString()); + Console.WriteLine(); + + Complex c3 = c1 * new Complex(2.5, 3.5); + Console.WriteLine(c3.ToString()); + c3 = c3 + new Complex(Double.MinValue / 2, Double.MaxValue / 2); + Console.WriteLine(c3); + } +} +// The example displays the following output: +// (NaN, NaN) +// (NaN, NaN) +// (NaN, Infinity) +// (NaN, Infinity) +// diff --git a/snippets/csharp/System.Numerics/Complex/Overview/precision1.cs b/snippets/csharp/System.Numerics/Complex/Overview/precision1.cs new file mode 100644 index 00000000000..c2e851c3b5a --- /dev/null +++ b/snippets/csharp/System.Numerics/Complex/Overview/precision1.cs @@ -0,0 +1,35 @@ +using System; +using System.Numerics; + +public class PrecisionEx +{ + public static void Run() + { + // + Complex value = new Complex(Double.MinValue / 2, Double.MinValue / 2); + Complex value2 = Complex.Exp(Complex.Log(value)); + Console.WriteLine($"{value} \n{value2} \nEqual: {value == value2}"); + // The example displays the following output: + // (-8.98846567431158E+307, -8.98846567431158E+307) + // (-8.98846567431161E+307, -8.98846567431161E+307) + // Equal: False + // + + Console.WriteLine(); + ShowPlatform(); + } + + private static void ShowPlatform() + { + // + Complex minusOne = new Complex(-1, 0); + Console.WriteLine(Complex.Sqrt(minusOne)); + // The example displays the following output: + // (6.12303176911189E-17, 1) on 32-bit systems. + // (6.12323399573677E-17,1) on IA64 systems. + // + } +} + +// Complex minusOne = new Complex(-1,0); +// Complex.Sqrt(minusOne) returns Complex(6.12303176911189E-17, 1) where as it returns Complex on IA64. diff --git a/snippets/fsharp/System.Collections.Generic/ListT/Overview/addremoveinsert.fs b/snippets/fsharp/System.Collections.Generic/ListT/Overview/addremoveinsert.fs new file mode 100644 index 00000000000..2909b9f54a6 --- /dev/null +++ b/snippets/fsharp/System.Collections.Generic/ListT/Overview/addremoveinsert.fs @@ -0,0 +1,66 @@ +// + +// Simple business object. A PartId is used to identify the type of part +// but the part name can change. +[] +type Part = { PartId : int ; mutable PartName : string } with + override this.GetHashCode() = hash this.PartId + override this.Equals(other) = + match other with + | :? Part as p -> this.PartId = p.PartId + | _ -> false + override this.ToString() = sprintf "ID: %i Name: %s" this.PartId this.PartName + +[] +let main argv = + // We refer to System.Collections.Generic.List<'T> by its type + // abbreviation ResizeArray<'T> to avoid conflicts with the F# List module. + // Note: In F# code, F# linked lists are usually preferred over + // ResizeArray<'T> when an extendable collection is required. + let parts = ResizeArray<_>() + parts.Add({PartName = "crank arm" ; PartId = 1234}) + parts.Add({PartName = "chain ring"; PartId = 1334 }) + parts.Add({PartName = "regular seat"; PartId = 1434 }) + parts.Add({PartName = "banana seat"; PartId = 1444 }) + parts.Add({PartName = "cassette"; PartId = 1534 }) + parts.Add({PartName = "shift lever"; PartId = 1634 }) + + // Write out the parts in the ResizeArray. This will call the overridden ToString method + // in the Part type + printfn "" + parts |> Seq.iter (fun p -> printfn "%O" p) + + // Check the ResizeArray for part #1734. This calls the IEquatable.Equals method + // of the Part type, which checks the PartId for equality. + printfn "\nContains(\"1734\"): %b" (parts.Contains({PartId=1734; PartName=""})) + + // Insert a new item at position 2. + printfn "\nInsert(2, \"1834\")" + parts.Insert(2, { PartName = "brake lever"; PartId = 1834 }) + + // Write out all parts + parts |> Seq.iter (fun p -> printfn "%O" p) + + printfn "\nParts[3]: %O" parts.[3] + + printfn "\nRemove(\"1534\")" + // This will remove part 1534 even though the PartName is different, + // because the Equals method only checks PartId for equality. + // Since Remove returns true or false, we need to ignore the result + parts.Remove({PartId=1534; PartName="cogs"}) |> ignore + + // Write out all parts + printfn "" + parts |> Seq.iter (fun p -> printfn "%O" p) + + printfn "\nRemoveAt(3)" + // This will remove the part at index 3. + parts.RemoveAt(3) + + // Write out all parts + printfn "" + parts |> Seq.iter (fun p -> printfn "%O" p) + + 0 // return an integer exit code + +// diff --git a/snippets/fsharp/System.Collections.Generic/ListT/Overview/listclass.fs b/snippets/fsharp/System.Collections.Generic/ListT/Overview/listclass.fs new file mode 100644 index 00000000000..7a462508dac --- /dev/null +++ b/snippets/fsharp/System.Collections.Generic/ListT/Overview/listclass.fs @@ -0,0 +1,100 @@ +// + +[] +let main argv = + // We refer to System.Collections.Generic.List<'T> by its type + // abbreviation ResizeArray<'T> to avoid conflict with the List module. + // Note: In F# code, F# linked lists are usually preferred over + // ResizeArray<'T> when an extendable collection is required. + let dinosaurs = ResizeArray<_>() + + // Write out the dinosaurs in the ResizeArray. + let printDinosaurs() = + printfn "" + dinosaurs |> Seq.iter (fun p -> printfn "%O" p) + + + printfn "\nCapacity: %i" dinosaurs.Capacity + + dinosaurs.Add("Tyrannosaurus") + dinosaurs.Add("Amargasaurus") + dinosaurs.Add("Mamenchisaurus") + dinosaurs.Add("Deinonychus") + dinosaurs.Add("Compsognathus") + + printDinosaurs() + + printfn "\nCapacity: %i" dinosaurs.Capacity + printfn "Count: %i" dinosaurs.Count + + printfn "\nContains(\"Deinonychus\"): %b" (dinosaurs.Contains("Deinonychus")) + + printfn "\nInsert(2, \"Compsognathus\")" + dinosaurs.Insert(2, "Compsognathus") + + printDinosaurs() + + // Shows accessing the list using the Item property. + printfn "\ndinosaurs[3]: %s" dinosaurs.[3] + + printfn "\nRemove(\"Compsognathus\")" + dinosaurs.Remove("Compsognathus") |> ignore + + printDinosaurs() + + dinosaurs.TrimExcess() + printfn "\nTrimExcess()" + printfn "Capacity: %i" dinosaurs.Capacity + printfn "Count: %i" dinosaurs.Count + + dinosaurs.Clear() + printfn "\nClear()" + printfn "Capacity: %i" dinosaurs.Capacity + printfn "Count: %i" dinosaurs.Count + + 0 // return an integer exit code + + (* This code example produces the following output: + +Capacity: 0 + +Tyrannosaurus +Amargasaurus +Mamenchisaurus +Deinonychus +Compsognathus + +Capacity: 8 +Count: 5 + +Contains("Deinonychus"): true + +Insert(2, "Compsognathus") + +Tyrannosaurus +Amargasaurus +Compsognathus +Mamenchisaurus +Deinonychus +Compsognathus + +dinosaurs[3]: Mamenchisaurus + +Remove("Compsognathus") + +Tyrannosaurus +Amargasaurus +Mamenchisaurus +Deinonychus +Compsognathus + +TrimExcess() +Capacity: 5 +Count: 5 + +Clear() +Capacity: 5 +Count: 0 + *) + +// diff --git a/snippets/visualbasic/System.Collections.Generic/List/Overview/Project.vbproj b/snippets/visualbasic/System.Collections.Generic/List/Overview/Project.vbproj new file mode 100644 index 00000000000..874c98f3477 --- /dev/null +++ b/snippets/visualbasic/System.Collections.Generic/List/Overview/Project.vbproj @@ -0,0 +1,8 @@ + + + + Library + net10.0 + + + diff --git a/snippets/visualbasic/System.Collections.Generic/List/Overview/module1.vb b/snippets/visualbasic/System.Collections.Generic/List/Overview/module1.vb new file mode 100644 index 00000000000..155af7209fe --- /dev/null +++ b/snippets/visualbasic/System.Collections.Generic/List/Overview/module1.vb @@ -0,0 +1,183 @@ +' + +' Simple business object. A PartId is used to identify the type of part +' but the part name can change. +Public Class Part + Implements IEquatable(Of Part) + Public Property PartName() As String + Get + Return m_PartName + End Get + Set(value As String) + m_PartName = value + End Set + End Property + Private m_PartName As String + + Public Property PartId() As Integer + Get + Return m_PartId + End Get + Set(value As Integer) + m_PartId = value + End Set + End Property + Private m_PartId As Integer + + Public Overrides Function ToString() As String + Return "ID: " & PartId & " Name: " & PartName + End Function + Public Overrides Function Equals(obj As Object) As Boolean + If obj Is Nothing Then + Return False + End If + Dim objAsPart As Part = TryCast(obj, Part) + If objAsPart Is Nothing Then + Return False + Else + Return Equals(objAsPart) + End If + End Function + Public Overrides Function GetHashCode() As Integer + Return PartId + End Function + Public Overloads Function Equals(other As Part) As Boolean _ + Implements IEquatable(Of Part).Equals + If other Is Nothing Then + Return False + End If + Return (Me.PartId.Equals(other.PartId)) + End Function + ' Should also override == and != operators. + +End Class +Public Class Example + Public Shared Sub Main() + ' Create a list of parts. + Dim parts As New List(Of Part)() + + ' Add parts to the list. + parts.Add(New Part() With { + .PartName = "crank arm", + .PartId = 1234 + }) + parts.Add(New Part() With { + .PartName = "chain ring", + .PartId = 1334 + }) + parts.Add(New Part() With { + .PartName = "regular seat", + .PartId = 1434 + }) + parts.Add(New Part() With { + .PartName = "banana seat", + .PartId = 1444 + }) + parts.Add(New Part() With { + .PartName = "cassette", + .PartId = 1534 + }) + parts.Add(New Part() With { + .PartName = "shift lever", + .PartId = 1634 + }) + + + + ' Write out the parts in the list. This will call the overridden ToString method + ' in the Part class. + Console.WriteLine() + For Each aPart As Part In parts + Console.WriteLine(aPart) + Next + + + ' Check the list for part #1734. This calls the IEquatable.Equals method + ' of the Part class, which checks the PartId for equality. + Console.WriteLine(vbLf & "Contains(""1734""): {0}", parts.Contains(New Part() With { + .PartId = 1734, + .PartName = "" + })) + + ' Insert a new item at position 2. + Console.WriteLine(vbLf & "Insert(2, ""1834"")") + parts.Insert(2, New Part() With { + .PartName = "brake lever", + .PartId = 1834 + }) + + + 'Console.WriteLine(); + For Each aPart As Part In parts + Console.WriteLine(aPart) + Next + + Console.WriteLine(vbLf & "Parts[3]: {0}", parts(3)) + + Console.WriteLine(vbLf & "Remove(""1534"")") + + ' This will remove part 1534 even though the PartName is different, + ' because the Equals method only checks PartId for equality. + parts.Remove(New Part() With { + .PartId = 1534, + .PartName = "cogs" + }) + + Console.WriteLine() + For Each aPart As Part In parts + Console.WriteLine(aPart) + Next + + Console.WriteLine(vbLf & "RemoveAt(3)") + ' This will remove part at index 3. + parts.RemoveAt(3) + + Console.WriteLine() + For Each aPart As Part In parts + Console.WriteLine(aPart) + Next + End Sub + ' + ' This example code produces the following output: + ' ID: 1234 Name: crank arm + ' ID: 1334 Name: chain ring + ' ID: 1434 Name: regular seat + ' ID: 1444 Name: banana seat + ' ID: 1534 Name: cassette + ' ID: 1634 Name: shift lever + ' + ' Contains("1734"): False + ' + ' Insert(2, "1834") + ' ID: 1234 Name: crank arm + ' ID: 1334 Name: chain ring + ' ID: 1834 Name: brake lever + ' ID: 1434 Name: regular seat + ' ID: 1444 Name: banana seat + ' ID: 1534 Name: cassette + ' ID: 1634 Name: shift lever + ' + ' Parts[3]: ID: 1434 Name: regular seat + ' + ' Remove("1534") + ' + ' ID: 1234 Name: crank arm + ' ID: 1334 Name: chain ring + ' ID: 1834 Name: brake lever + ' ID: 1434 Name: regular seat + ' ID: 1444 Name: banana seat + ' ID: 1634 Name: shift lever + ' ' + ' RemoveAt(3) + ' + ' ID: 1234 Name: crank arm + ' ID: 1334 Name: chain ring + ' ID: 1834 Name: brake lever + ' ID: 1444 Name: banana seat + ' ID: 1634 Name: shift lever + ' + +End Class +' + + diff --git a/snippets/visualbasic/System.Collections.Generic/List/Overview/source.vb b/snippets/visualbasic/System.Collections.Generic/List/Overview/source.vb new file mode 100644 index 00000000000..99fd775472d --- /dev/null +++ b/snippets/visualbasic/System.Collections.Generic/List/Overview/source.vb @@ -0,0 +1,100 @@ +' +Public Class Example2 + + Public Shared Sub Main() + ' + Dim dinosaurs As New List(Of String) + + Console.WriteLine(vbLf & "Capacity: {0}", dinosaurs.Capacity) + + dinosaurs.Add("Tyrannosaurus") + dinosaurs.Add("Amargasaurus") + dinosaurs.Add("Mamenchisaurus") + dinosaurs.Add("Deinonychus") + dinosaurs.Add("Compsognathus") + ' + + Console.WriteLine() + For Each dinosaur As String In dinosaurs + Console.WriteLine(dinosaur) + Next + + Console.WriteLine(vbLf & "Capacity: {0}", dinosaurs.Capacity) + Console.WriteLine("Count: {0}", dinosaurs.Count) + + Console.WriteLine(vbLf & "Contains(""Deinonychus""): {0}", + dinosaurs.Contains("Deinonychus")) + + Console.WriteLine(vbLf & "Insert(2, ""Compsognathus"")") + dinosaurs.Insert(2, "Compsognathus") + + Console.WriteLine() + For Each dinosaur As String In dinosaurs + Console.WriteLine(dinosaur) + Next + ' + ' Shows how to access the list using the Item property. + Console.WriteLine(vbLf & "dinosaurs(3): {0}", dinosaurs(3)) + ' + Console.WriteLine(vbLf & "Remove(""Compsognathus"")") + dinosaurs.Remove("Compsognathus") + + Console.WriteLine() + For Each dinosaur As String In dinosaurs + Console.WriteLine(dinosaur) + Next + + dinosaurs.TrimExcess() + Console.WriteLine(vbLf & "TrimExcess()") + Console.WriteLine("Capacity: {0}", dinosaurs.Capacity) + Console.WriteLine("Count: {0}", dinosaurs.Count) + + dinosaurs.Clear() + Console.WriteLine(vbLf & "Clear()") + Console.WriteLine("Capacity: {0}", dinosaurs.Capacity) + Console.WriteLine("Count: {0}", dinosaurs.Count) + End Sub +End Class + +' This code example produces the following output: +' +'Capacity: 0 +' +'Tyrannosaurus +'Amargasaurus +'Mamenchisaurus +'Deinonychus +'Compsognathus +' +'Capacity: 8 +'Count: 5 +' +'Contains("Deinonychus"): True +' +'Insert(2, "Compsognathus") +' +'Tyrannosaurus +'Amargasaurus +'Compsognathus +'Mamenchisaurus +'Deinonychus +'Compsognathus +' +'dinosaurs(3): Mamenchisaurus +' +'Remove("Compsognathus") +' +'Tyrannosaurus +'Amargasaurus +'Mamenchisaurus +'Deinonychus +'Compsognathus +' +'TrimExcess() +'Capacity: 5 +'Count: 5 +' +'Clear() +'Capacity: 5 +'Count: 0 +' diff --git a/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb b/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb new file mode 100644 index 00000000000..7416d8050f4 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb @@ -0,0 +1,86 @@ +' Visual Basic .NET Document +Option Strict On + +Imports System.Numerics + +Module Example1 + Public Sub Main() + ' + Dim bigIntFromDouble As New BigInteger(179032.6541) + Console.WriteLine(bigIntFromDouble) + Dim bigIntFromInt64 As New BigInteger(934157136952) + Console.WriteLine(bigIntFromInt64) + ' The example displays the following output: + ' 179032 + ' 934157136952 + ' + + Console.WriteLine() + + ' + Dim longValue As Long = 6315489358112 + Dim assignedFromLong As BigInteger = longValue + Console.WriteLine(assignedFromLong) + ' The example displays the following output: + ' 6315489358112 + ' + + Console.WriteLine() + + ' + Dim assignedFromDouble As BigInteger = CType(179032.6541, BigInteger) + Console.WriteLine(assignedFromDouble) + Dim assignedFromDecimal As BigInteger = CType(64312.65D, BigInteger) + Console.WriteLine(assignedFromDecimal) + ' The example displays the following output: + ' 179032 + ' 64312 + ' + + Console.WriteLine() + + ' + Dim byteArray() As Byte = {10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0} + Dim newBigInt As New BigInteger(byteArray) + Console.WriteLine("The value of newBigInt is {0} (or 0x{0:x}).", newBigInt) + ' The example displays the following output: + ' The value of newBigInt is 4759477275222530853130 (or 0x102030405060708090a). + ' + + Console.WriteLine() + + ' + Dim positiveString As String = "91389681247993671255432112000000" + Dim negativeString As String = "-90315837410896312071002088037140000" + Dim posBigInt As BigInteger = 0 + Dim negBigInt As BigInteger = 0 + + Try + posBigInt = BigInteger.Parse(positiveString) + Console.WriteLine(posBigInt) + Catch e As FormatException + Console.WriteLine("Unable to convert the string '{0}' to a BigInteger value.", + positiveString) + End Try + + If BigInteger.TryParse(negativeString, negBigInt) Then + Console.WriteLine(negBigInt) + Else + Console.WriteLine("Unable to convert the string '{0}' to a BigInteger value.", + negativeString) + End If + ' The example displays the following output: + ' 9.1389681247993671255432112E+31 + ' -9.0315837410896312071002088037E+34 + ' + + Console.WriteLine() + + ' + Dim number As BigInteger = BigInteger.Pow(UInt64.MaxValue, 3) + Console.WriteLine(number) + ' The example displays the following output: + ' 6277101735386680762814942322444851025767571854389858533375 + ' + End Sub +End Module diff --git a/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb b/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb new file mode 100644 index 00000000000..3cf3022a05f --- /dev/null +++ b/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb @@ -0,0 +1,154 @@ +' Visual Basic .NET Document +Option Strict On + +Imports System.Globalization +Imports System.Numerics + +Module Example + Public Sub Main() + RoundtripBigInteger() + Console.WriteLIne() + RoundtripInt16() + Console.WriteLine() + HandleSignsInByteArray() + Console.WriteLine() + RoundtripAmbiguous() + Console.WriteLine() + RoundtripWithHex() + Console.WriteLine() + End Sub + + Private Sub RoundTripBigInteger() + Console.WriteLine("Round-trip bytes") + + ' + Dim number As BigInteger = BigInteger.Pow(Int64.MaxValue, 2) + Console.WriteLine(number) + + ' Write the BigInteger value to a byte array. + Dim bytes() As Byte = number.ToByteArray() + + ' Display the byte array. + For Each byteValue As Byte In bytes + Console.Write("0x{0:X2} ", byteValue) + Next + Console.WriteLine() + + ' Restore the BigInteger value from a Byte array. + Dim newNumber As BigInteger = New BigInteger(bytes) + Console.WriteLine(newNumber) + ' The example displays the following output: + ' 8.5070591730234615847396907784E+37 + ' 0x01 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0x3F + ' + ' 8.5070591730234615847396907784E+37 + ' + End Sub + + Private Sub RoundTripInt16() + Console.WriteLine() + Console.WriteLine("Round-trip an Int16 value:") + ' + Dim originalValue As Short = 30000 + Console.WriteLine(originalValue) + + ' Convert the Int16 value to a byte array. + Dim bytes() As Byte = BitConverter.GetBytes(originalValue) + + ' Display the byte array. + For Each byteValue As Byte In bytes + Console.Write("0x{0} ", byteValue.ToString("X2")) + Next + Console.WriteLine() + + ' Pass byte array to the BigInteger constructor. + Dim number As BigInteger = New BigInteger(bytes) + Console.WriteLine(number) + ' The example displays the following output: + ' 30000 + ' 0x30 0x75 + ' 30000 + ' + End Sub + + PRivate Sub HandleSignsInByteArray() + ' + Dim negativeNumber As Integer = -1000000 + Dim positiveNumber As UInteger = 4293967296 + + Dim negativeBytes() As Byte = BitConverter.GetBytes(negativeNumber) + Dim negativeBigInt As New BigInteger(negativeBytes) + Console.WriteLine(negativeBigInt.ToString("N0")) + + Dim tempPosBytes() As Byte = BitConverter.GetBytes(positiveNumber) + Dim positiveBytes(tempposBytes.Length) As Byte + Array.Copy(tempPosBytes, positiveBytes, tempPosBytes.Length) + Dim positiveBigInt As New BigInteger(positiveBytes) + Console.WriteLine(positiveBigInt.ToString("N0")) + ' The example displays the following output: + ' -1,000,000 + ' 4,293,967,296 + ' + End Sub + + Private Sub RoundtripAmbiguous() + ' + Dim positiveValue As BigInteger = 15777216 + Dim negativeValue As BigInteger = -1000000 + + Console.WriteLine("Positive value: " + positiveValue.ToString("N0")) + Dim bytes() As Byte = positiveValue.ToByteArray() + For Each byteValue As Byte In bytes + Console.Write("{0:X2} ", byteValue) + Next + Console.WriteLine() + positiveValue = New BigInteger(bytes) + Console.WriteLine("Restored positive value: " + positiveValue.ToString("N0")) + + Console.WriteLine() + + Console.WriteLIne("Negative value: " + negativeValue.ToString("N0")) + bytes = negativeValue.ToByteArray() + For Each byteValue As Byte In bytes + Console.Write("{0:X2} ", byteValue) + Next + Console.WriteLine() + negativeValue = New BigInteger(bytes) + Console.WriteLine("Restored negative value: " + negativeValue.ToString("N0")) + ' The example displays the following output: + ' Positive value: 15,777,216 + ' C0 BD F0 00 + ' Restored positive value: 15,777,216 + ' + ' Negative value: -1,000,000 + ' C0 BD F0 + ' Restored negative value: -1,000,000 + ' + End Sub + + Private Sub RoundtripWithHex() + ' + Dim negativeNumber As BigInteger = -1000000 + Dim positiveNumber As BigInteger = 15777216 + + Dim negativeHex As String = negativeNumber.ToString("X") + Dim positiveHex As string = positiveNumber.ToString("X") + + Dim negativeNumber2, positiveNumber2 As BigInteger + negativeNumber2 = BigInteger.Parse(negativeHex, + NumberStyles.HexNumber) + positiveNumber2 = BigInteger.Parse(positiveHex, + NumberStyles.HexNumber) + + Console.WriteLine("Converted {0:N0} to {1} back to {2:N0}.", + negativeNumber, negativeHex, negativeNumber2) + Console.WriteLine("Converted {0:N0} to {1} back to {2:N0}.", + positiveNumber, positiveHex, positiveNumber2) + ' The example displays the following output: + ' Converted -1,000,000 to F0BDC0 back to -1,000,000. + ' Converted 15,777,216 to 0F0BDC0 back to 15,777,216. + ' + End Sub + +End Module + diff --git a/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.vb b/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.vb new file mode 100644 index 00000000000..6f649590f1c --- /dev/null +++ b/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.vb @@ -0,0 +1,45 @@ +' Visual Basic .NET Document +Option Strict On + +' +Imports System.Globalization +Imports System.Numerics + +Public Structure HexValue + Public Sign As Integer + Public Value As String +End Structure + +Module Example2 + Public Sub Main() + Dim positiveNumber As UInteger = 4039543321 + Dim negativeNumber As Integer = -255423975 + + ' Convert the numbers to hex strings. + Dim hexValue1, hexValue2 As HexValue + hexValue1.Value = positiveNumber.ToString("X") + hexValue1.Sign = Math.Sign(positiveNumber) + + hexValue2.Value = Convert.ToString(negativeNumber, 16) + hexValue2.Sign = Math.Sign(negativeNumber) + + ' Round-trip the hexadecimal values to BigInteger values. + Dim hexString As String + Dim positiveBigInt, negativeBigInt As BigInteger + + hexString = CStr(IIf(hexValue1.Sign = 1, "0", "")) + hexValue1.Value + positiveBigInt = BigInteger.Parse(hexString, NumberStyles.HexNumber) + Console.WriteLine("Converted {0} to {1} and back to {2}.", + positiveNumber, hexValue1.Value, positiveBigInt) + + hexString = CStr(IIf(hexValue2.Sign = 1, "0", "")) + hexValue2.Value + negativeBigInt = BigInteger.Parse(hexString, NumberStyles.HexNumber) + Console.WriteLine("Converted {0} to {1} and back to {2}.", + negativeNumber, hexValue2.Value, negativeBigInt) + + End Sub +End Module +' The example displays the following output: +' Converted 4039543321 to F0C68A19 and back to 4039543321. +' Converted -255423975 to f0c68a19 and back to -255423975. +' diff --git a/snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb b/snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb new file mode 100644 index 00000000000..015b627a072 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb @@ -0,0 +1,69 @@ +' Visual Basic .NET Document +'Option Strict On + +Imports System.Diagnostics +Imports System.Numerics + +Module Example3 + Public Sub Main() + ShowSimpleAdd() + PerformBigIntegerOperation() + PerformWithIntermediary() + End Sub + + Private Sub ShowSimpleAdd() + ' + Dim number As BigInteger = BigInteger.Multiply(Int64.MaxValue, 3) + number += 1 + Console.WriteLine(number) + ' + End Sub + + Private Sub PerformBigIntegerOperation() + Dim sw As Stopwatch = Stopwatch.StartNew() + + ' + Dim number As BigInteger = Int64.MaxValue ^ 5 + Dim repetitions As Integer = 1000000 + ' Perform some repetitive operation 1 million times. + For ctr As Integer = 0 To repetitions + ' Perform some operation. If it fails, exit the loop. + If Not SomeOperationSucceeds() Then Exit For + ' The following code executes if the operation succeeds. + number += 1 + Next + ' + + sw.Stop() + Console.WriteLine("Incrementing a BigInteger: " + sw.Elapsed.ToString()) + End Sub + + Private Sub PerformWithIntermediary() + Dim sw As Stopwatch = Stopwatch.StartNew() + + ' + Dim number As BigInteger = Int64.MaxValue ^ 5 + Dim repetitions As Integer = 1000000 + Dim actualRepetitions As Integer = 0 + ' Perform some repetitive operation 1 million times. + For ctr As Integer = 0 To repetitions + ' Perform some operation. If it fails, exit the loop. + If Not SomeOperationSucceeds() Then Exit For + ' The following code executes if the operation succeeds. + actualRepetitions += 1 + Next + number += actualRepetitions + ' + + sw.Stop() + Console.WriteLine("Incrementing a BigInteger: " + sw.Elapsed.ToString()) + End Sub + + Private Function SomeOperationSucceeds() As Boolean + Return True + End Function +End Module + +' +' CAPS bug: snippet2 is seen as duplicated, even though it isn't. +' diff --git a/snippets/visualbasic/System.Numerics/BigInteger/Overview/Project.vbproj b/snippets/visualbasic/System.Numerics/BigInteger/Overview/Project.vbproj new file mode 100644 index 00000000000..874c98f3477 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/BigInteger/Overview/Project.vbproj @@ -0,0 +1,8 @@ + + + + Library + net10.0 + + + diff --git a/snippets/visualbasic/System.Numerics/Complex/Overview/Program.vb b/snippets/visualbasic/System.Numerics/Complex/Overview/Program.vb new file mode 100644 index 00000000000..8cd0a0ebcc1 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/Complex/Overview/Program.vb @@ -0,0 +1,5 @@ +Public Class Program + Public Shared Sub Main() + Example2.Run() + End Sub +End Class diff --git a/snippets/visualbasic/System.Numerics/Complex/Overview/Project.vbproj b/snippets/visualbasic/System.Numerics/Complex/Overview/Project.vbproj new file mode 100644 index 00000000000..f99395b4b2b --- /dev/null +++ b/snippets/visualbasic/System.Numerics/Complex/Overview/Project.vbproj @@ -0,0 +1,8 @@ + + + + Exe + net10.0 + + + diff --git a/snippets/visualbasic/System.Numerics/Complex/Overview/create1.vb b/snippets/visualbasic/System.Numerics/Complex/Overview/create1.vb new file mode 100644 index 00000000000..fdfaf392596 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/Complex/Overview/create1.vb @@ -0,0 +1,41 @@ +' Visual Basic .NET Document +Option Strict On + +' +Imports System.Numerics + +Module Example + Public Sub Run() + ' Create a complex number by calling its class constructor. + Dim c1 As New Complex(12, 6) + Console.WriteLine(c1) + + ' Assign a Double to a complex number. + Dim c2 As Complex = 3.14 + Console.WriteLine(c2) + + ' Cast a Decimal to a complex number. + Dim c3 As Complex = CType(12.3d, Complex) + Console.WriteLine(c3) + + ' Assign the return value of a method to a Complex variable. + Dim c4 As Complex = Complex.Pow(Complex.One, -1) + Console.WriteLine(c4) + + ' Assign the value returned by an operator to a Complex variable. + Dim c5 As Complex = Complex.One + Complex.One + Console.WriteLine(c5) + + ' Instantiate a complex number from its polar coordinates. + Dim c6 As Complex = Complex.FromPolarCoordinates(10, .524) + Console.WriteLine(c6) + End Sub +End Module +' The example displays the following output: +' (12, 6) +' (3.14, 0) +' (12.3000001907349, 0) +' (1, 0) +' (2, 0) +' (8.65824721882145, 5.00347430269914) +' diff --git a/snippets/visualbasic/System.Numerics/Complex/Overview/customfmt1.vb b/snippets/visualbasic/System.Numerics/Complex/Overview/customfmt1.vb new file mode 100644 index 00000000000..61ee5de6b18 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/Complex/Overview/customfmt1.vb @@ -0,0 +1,76 @@ +' Visual Basic .NET Document +Option Strict On + +' +Imports System.Numerics + +Public Class ComplexFormatter + Implements IFormatProvider, ICustomFormatter + + Public Function GetFormat(formatType As Type) As Object _ + Implements IFormatProvider.GetFormat + If formatType Is GetType(ICustomFormatter) Then + Return Me + Else + Return Nothing + End If + End Function + + Public Function Format(fmt As String, arg As Object, + provider As IFormatProvider) As String _ + Implements ICustomFormatter.Format + If TypeOf arg Is Complex Then + Dim c1 As Complex = DirectCast(arg, Complex) + ' Check if the format string has a precision specifier. + Dim precision As Integer + Dim fmtString As String = String.Empty + If fmt.Length > 1 Then + Try + precision = Integer.Parse(fmt.Substring(1)) + Catch e As FormatException + precision = 0 + End Try + fmtString = "N" + precision.ToString() + End If + ' Determine the sign to display. + Dim sign As Char = If(c1.Imaginary < 0.0, "-"c, "+"c) + ' Display the determined sign and the absolute value of the imaginary part. + If fmt.Substring(0, 1).Equals("I", StringComparison.OrdinalIgnoreCase) Then + Return c1.Real.ToString(fmtString) + " " + sign + " " + Math.Abs(c1.Imaginary).ToString(fmtString) + "i" + ElseIf fmt.Substring(0, 1).Equals("J", StringComparison.OrdinalIgnoreCase) Then + Return c1.Real.ToString(fmtString) + " " + sign + " " + Math.Abs(c1.Imaginary).ToString(fmtString) + "j" + Else + Return c1.ToString(fmt, provider) + End If + Else + If TypeOf arg Is IFormattable Then + Return DirectCast(arg, IFormattable).ToString(fmt, provider) + ElseIf arg IsNot Nothing Then + Return arg.ToString() + Else + Return String.Empty + End If + End If + End Function +End Class +' + +' +Module Example2 + Public Sub Run() + Dim c1 As New Complex(12.1, 15.4) + Console.WriteLine($"Formatting with ToString(): {c1}") + Console.WriteLine($"Formatting with ToString(format): {c1:N2}") + Console.WriteLine($"Custom formatting with I0: " + + $"{String.Format(New ComplexFormatter(), "{0:I0}", c1)}") + Console.WriteLine($"Custom formatting with J3: " + + $"{String.Format(New ComplexFormatter(), "{0:J3}", c1)}") + End Sub +End Module + +' The example displays the following output: +' Formatting with ToString(): <12.1; 15.4> +' Formatting with ToString(format): <12.10; 15.40> +' Custom formatting with I0: 12 + 15i +' Custom formatting with J3: 12.100 + 15.400j +' diff --git a/snippets/visualbasic/System.Numerics/Complex/Overview/nan1.vb b/snippets/visualbasic/System.Numerics/Complex/Overview/nan1.vb new file mode 100644 index 00000000000..b794990719e --- /dev/null +++ b/snippets/visualbasic/System.Numerics/Complex/Overview/nan1.vb @@ -0,0 +1,29 @@ +' Visual Basic .NET Document +Option Strict On + +' +Imports System.Numerics + +Module Example4 + Public Sub Run() + Dim c1 As Complex = New Complex(Double.MaxValue / 2, Double.MaxValue / 2) + + Dim c2 As Complex = c1 / Complex.Zero + Console.WriteLine(c2.ToString()) + c2 = c2 * New Complex(1.5, 1.5) + Console.WriteLine(c2.ToString()) + Console.WriteLine() + + Dim c3 As Complex = c1 * New Complex(2.5, 3.5) + Console.WriteLine(c3.ToString()) + c3 = c3 + New Complex(Double.MinValue / 2, Double.MaxValue / 2) + Console.WriteLine(c3) + End Sub +End Module +' The example displays the following output: +' (NaN, NaN) +' (NaN, NaN) +' +' (NaN, Infinity) +' (NaN, Infinity) +' diff --git a/snippets/visualbasic/System.Numerics/Complex/Overview/precision1.vb b/snippets/visualbasic/System.Numerics/Complex/Overview/precision1.vb new file mode 100644 index 00000000000..32247a08f22 --- /dev/null +++ b/snippets/visualbasic/System.Numerics/Complex/Overview/precision1.vb @@ -0,0 +1,35 @@ +' Visual Basic .NET Document +Option Strict On + +Imports System.Numerics + +Module Example3 + Public Sub Run() + ' + Dim value As New Complex(Double.MinValue / 2, Double.MinValue / 2) + Dim value2 As Complex = Complex.Exp(Complex.Log(value)) + Console.WriteLine("{0} {3}{1} {3}Equal: {2}", value, value2, + value = value2, + vbCrLf) + ' The example displays the following output: + ' (-8.98846567431158E+307, -8.98846567431158E+307) + ' (-8.98846567431161E+307, -8.98846567431161E+307) + ' Equal: False + ' + + Console.WriteLine() + ShowPlatform() + End Sub + + + Private Sub ShowPlatform() + ' + Dim minusOne As New Complex(-1, 0) + Console.WriteLine(Complex.Sqrt(minusOne)) + ' The example displays the following output: + ' (6.12303176911189E-17, 1) on 32-bit systems. + ' (6.12323399573677E-17,1) on IA64 systems. + ' + End Sub +End Module + diff --git a/xml/Microsoft.Win32/Registry.xml b/xml/Microsoft.Win32/Registry.xml index 4b77280f929..95bff860a7b 100644 --- a/xml/Microsoft.Win32/Registry.xml +++ b/xml/Microsoft.Win32/Registry.xml @@ -38,7 +38,39 @@ Provides objects that represent the root keys in the Windows registry, and methods to access key/value pairs. - For more information about this API, see Microsoft.Win32.Registry class. + + class provides the set of standard root keys found in the registry on machines running Windows. The registry is a storage facility for information about applications, users, and default system settings. Applications can use the registry for storing information that needs to be preserved after the application is closed, and access that same information when the application is reloaded. For example, you can store color preferences, screen locations, or the size of a window. You can control this data for each user by storing the information in a different location in the registry. + +The base, or root, instances that are exposed by the `Registry` class delineate the basic storage mechanism for subkeys and values in the registry. All keys are read-only because the registry depends on their existence. The keys exposed by `Registry` are: + +| Key | Description | +|-------------------------------------------------|--------------------------------------------------------------------| +| | Stores information about user preferences. | +| | Stores configuration information for the local machine. | +| | Stores information about types (and classes) and their properties. | +| | Stores information about the default user configuration. | +| | Stores performance information for software components. | +| | Stores non-user-specific hardware information. | +| | Stores dynamic data. | + +Once you've identified the root key under which you want to store/retrieve information from the registry, you can use the class to add or remove subkeys and manipulate the values for a given key. + +Hardware devices can place information in the registry automatically using the Plug and Play interface. Software for installing device drivers can place information in the registry by writing to standard APIs. + +## Static methods for getting and setting values + +The class also contains `static` and methods for setting and retrieving values from registry keys. These methods open and close registry keys each time they're used. So when you access a large number of values, they don't perform as well as analogous methods in the class. + +The class also provides methods that allow you to: + +- Set Windows access control security for registry keys. +- Test the data type of a value before retrieving it. +- Delete keys. + + ]]> + method to create an instance of the particular subkey of interest. You can then use other operations in `RegistryKey` to manipulate that key. diff --git a/xml/System.Collections.Generic/HashSet`1.xml b/xml/System.Collections.Generic/HashSet`1.xml index dc46c696ac9..1c1d34d6199 100644 --- a/xml/System.Collections.Generic/HashSet`1.xml +++ b/xml/System.Collections.Generic/HashSet`1.xml @@ -98,7 +98,58 @@ The type of elements in the hash set. Represents a set of values. - For more information about this API, see Supplemental API remarks for HashSet<T>. + + class provides high-performance set operations. A set is a collection that contains no duplicate elements, and whose elements are in no particular order. + +The capacity of a object is the number of elements that the object can hold. A object's capacity automatically increases as elements are added to the object. + +The class is based on the model of mathematical sets and provides high-performance set operations similar to accessing the keys of the or collections. In simple terms, the class can be thought of as a collection without values. + +A collection is not sorted and cannot contain duplicate elements. If order or element duplication is more important than performance for your application, consider using the class together with the method. + + provides many mathematical set operations, such as set addition (unions) and set subtraction. The following table lists the provided operations and their mathematical equivalents. + +|HashSet operation|Mathematical equivalent| +|-------------------------------|-----------------------------| +||Union or set addition| +||Intersection| +||Set subtraction| +||Symmetric difference| + +In addition to the listed set operations, the class also provides methods for determining set equality, overlap of sets, and whether a set is a subset or superset of another set. + +**.NET Framework only:** For very large objects, you can increase the maximum capacity to 2 billion elements on a 64-bit system by setting the `enabled` attribute of the [``](/dotnet/framework/configure-apps/file-schema/runtime/gcallowverylargeobjects-element) configuration element to `true` in the runtime environment. + +The class implements the interface. + +## HashSet and LINQ set operations + +LINQ provides access to the `Distinct`, `Union`, `Intersect`, and `Except` set operations on any data source that implements the or interfaces. provides a larger and more robust collection of set operations. For example, provides comparisons such as and . + +The primary difference between LINQ set operations and operations is that LINQ set operations always return a new collection, whereas the equivalent methods modify the current collection. + +Typically, if you must create a new set or if your application needs access only to the provided set operations, using LINQ set operations on any collection or array will be sufficient. However, if your application requires access to additional set operations, or if it is not desirable or necessary to create a new collection, use the class. + +The following table shows the operations and their equivalent LINQ set operations. + +|HashSet operation|LINQ equivalent| +|-------------------------------|---------------------| +||| +||| +||| +|Not provided.|| +||Not provided.| +||Not provided.| +||Not provided.| +||Not provided.| +||Not provided.| +||Not provided.| +||Not provided.| + + ]]> + objects and populates them with even and odd numbers, respectively. A third object is created from the set that contains the even numbers. The example then calls the method, which adds the odd number set to the third set. diff --git a/xml/System.Collections.Generic/List`1.xml b/xml/System.Collections.Generic/List`1.xml index 77630bdba5d..c524b69629a 100644 --- a/xml/System.Collections.Generic/List`1.xml +++ b/xml/System.Collections.Generic/List`1.xml @@ -88,7 +88,69 @@ The type of elements in the list. Represents a strongly typed list of objects that can be accessed by index. Provides methods to search, sort, and manipulate lists. - For more information about this API, see Supplemental API remarks for List<T>. + + class is the generic equivalent of the class. It implements the generic interface by using an array whose size is dynamically increased as required. + +You can add items to a by using the or methods. + +The class uses both an equality comparer and an ordering comparer. + +- Methods such as , , , and use an equality comparer for the list elements. The default equality comparer for type `T` is determined as follows. If type `T` implements the generic interface, then the equality comparer is the method of that interface; otherwise, the default equality comparer is . + +- Methods such as and use an ordering comparer for the list elements. The default comparer for type `T` is determined as follows. If type `T` implements the generic interface, then the default comparer is the method of that interface; otherwise, if type `T` implements the nongeneric interface, then the default comparer is the method of that interface. If type `T` implements neither interface, then there is no default comparer, and a comparer or comparison delegate must be provided explicitly. + +The is not guaranteed to be sorted. You must sort the before performing operations (such as ) that require the to be sorted. + +Elements in this collection can be accessed using an integer index. Indexes in this collection are zero-based. + +**.NET Framework only:** For very large objects, you can increase the maximum capacity to 2 billion elements on a 64-bit system by setting the `enabled` attribute of the [``](/dotnet/framework/configure-apps/file-schema/runtime/gcallowverylargeobjects-element) configuration element to `true` in the runtime environment. + + accepts `null` as a valid value for reference types and allows duplicate elements. + +For an immutable version of the class, see . + +## Performance considerations + +In deciding whether to use the or class, both of which have similar functionality, remember that the class performs better in most cases and is type safe. If a reference type is used for type `T` of the class, the behavior of the two classes is identical. However, if a value type is used for type `T`, you need to consider implementation and boxing issues. + +If a value type is used for type `T`, the compiler generates an implementation of the class specifically for that value type. That means a list element of a object does not have to be boxed before the element can be used, and after about 500 list elements are created, the memory saved by not boxing list elements is greater than the memory used to generate the class implementation. + +Make certain the value type used for type `T` implements the generic interface. If not, methods such as must call the method, which boxes the affected list element. If the value type implements the interface and you own the source code, also implement the generic interface to prevent the and methods from boxing list elements. If you do not own the source code, pass an object to the and methods. + +It's to your advantage to use the type-specific implementation of the class instead of using the class or writing a strongly typed wrapper collection yourself. That's because your implementation must do what .NET does for you already, and the .NET runtime can share common intermediate language code and metadata, which your implementation cannot. + +## F# considerations + +The class is used infrequently in F# code. Instead, [Lists](/dotnet/fsharp/language-reference/lists), which are immutable, singly-linked lists, are typically preferred. An F# `List` provides an ordered, immutable series of values, and is supported for use in functional-style development. When used from F#, the class is typically referred to by the `ResizeArray<'T>` type abbreviation to avoid naming conflicts with F# Lists. + +## Examples + +The following example demonstrates how to add, remove, and insert a simple business object in a . + +:::code language="csharp" source="~/snippets/csharp/System.Collections.Generic/ListT/Overview/program.cs" id="snippet1"::: +:::code language="vb" source="~/snippets/visualbasic/System.Collections.Generic/List/Overview/module1.vb" id="snippet1"::: +:::code language="fsharp" source="~/snippets/fsharp/System.Collections.Generic/ListT/Overview/addremoveinsert.fs" id="snippet1"::: + +The following example demonstrates several properties and methods of the generic class of type string. (For an example of a of complex types, see the method.) + +The parameterless constructor is used to create a list of strings with the default capacity. The property is displayed and then the method is used to add several items. The items are listed, and the property is displayed again, along with the property, to show that the capacity has been increased as needed. + +The method is used to test for the presence of an item in the list, the method is used to insert a new item in the middle of the list, and the contents of the list are displayed again. + +The default property (the indexer in C#) is used to retrieve an item, the method is used to remove the first instance of the duplicate item added earlier, and the contents are displayed again. The method always removes the first instance it encounters. + +The method is used to reduce the capacity to match the count, and the and properties are displayed. If the unused capacity had been less than 10 percent of total capacity, the list would not have been resized. + +Finally, the method is used to remove all items from the list, and the and properties are displayed. + +:::code language="csharp" source="~/snippets/csharp/System.Collections.Generic/ListT/Overview/source.cs" id="Snippet1"::: +:::code language="vb" source="~/snippets/visualbasic/System.Collections.Generic/List/Overview/source.vb" id="Snippet1"::: +:::code language="fsharp" source="~/snippets/fsharp/System.Collections.Generic/ListT/Overview/listclass.fs" id="Snippet1"::: + + ]]> + Public static ( in Visual Basic) members of this type are thread safe. Any instance members are not guaranteed to be thread safe. It is safe to perform multiple read operations on a , but issues can occur if the collection is modified while it's being read. To ensure thread safety, lock the collection during a read or write operation. To enable a collection to be accessed by multiple threads for reading and writing, you must implement your own synchronization. For collections with built-in synchronization, see the classes in the namespace. For an inherently thread-safe alternative, see the class. diff --git a/xml/System.Collections.ObjectModel/KeyedCollection`2.xml b/xml/System.Collections.ObjectModel/KeyedCollection`2.xml index c62175a0cf6..9cb376d5cf0 100644 --- a/xml/System.Collections.ObjectModel/KeyedCollection`2.xml +++ b/xml/System.Collections.ObjectModel/KeyedCollection`2.xml @@ -383,7 +383,25 @@ The element to change the key of. The new key for . Changes the key associated with the specified element in the lookup dictionary. - For more information about this API, see Supplemental API remarks for KeyedCollection<TKey,TItem>.ChangeItemKey. + + method does not modify the key embedded in `item`; it simply replaces the key saved in the lookup dictionary. Therefore, if `newKey` is different from the key that is embedded in `item`, you cannot access `item` by using the key returned by . + +This method does nothing if the does not have a lookup dictionary. + +Every key in a must be unique. A key cannot be `null`. + +This method is an O(1) operation. + +## Notes for implementers + +Before modifying the key embedded in an item, you must call this method to update the key in the lookup dictionary. If the dictionary creation threshold is -1, calling this method is not necessary. + +Do not expose the method as a public method of a derived class. Misuse of this method puts the lookup dictionary out of sync with item keys. For example, setting the key to `null` and then setting it to another value adds multiple keys for an item to the lookup dictionary. Expose this method internally to allow mutable item keys: When the key for an item changes, this method is used to change the key in the lookup dictionary. + + ]]> + method to support mutable keys, and how to override the protected , , , and methods to maintain the integrity of the keys and the collection. diff --git a/xml/System.Collections.ObjectModel/ObservableCollection`1.xml b/xml/System.Collections.ObjectModel/ObservableCollection`1.xml index 4e4ab7cb628..6f7dc09af49 100644 --- a/xml/System.Collections.ObjectModel/ObservableCollection`1.xml +++ b/xml/System.Collections.ObjectModel/ObservableCollection`1.xml @@ -77,7 +77,38 @@ The type of elements in the collection. Represents a dynamic data collection that provides notifications when items get added or removed, or when the whole list is refreshed. - For more information about this API, see Supplemental API remarks for ObservableCollection<T>. + + class represents a dynamic data collection that provides notifications when items get added or removed, or when the whole list is refreshed. + +In many cases, the data that you work with is a collection of objects. For example, a common scenario in data binding is to use an such as a , , or to display a collection of records. + +You can enumerate over any collection that implements the interface. However, to set up dynamic bindings so that insertions or deletions in the collection update the UI automatically, the collection must implement the interface. This interface exposes the event, an event that should be raised whenever the underlying collection changes. + +The class is a data collection type that implements the interface. + +Before implementing your own collection, consider using or one of the existing collection classes, such as , , and , among many others. If you have an advanced scenario and want to implement your own collection, consider using , which provides a non-generic collection of objects that can be individually accessed by index. Implementing provides the best performance with the data binding engine. + +> [!NOTE] +> To fully support transferring data values from binding source objects to binding targets, each object in your collection that supports bindable properties must implement an appropriate property changed notification mechanism such as the interface. + +For more information, see "Binding to Collections" in [Data Binding Overview](/dotnet/framework/wpf/data/data-binding-overview). + +## Notes on XAML usage + + can be used as a XAML object element in Windows Presentation Foundation (WPF), in versions 3.0 and 3.5. However, the usage has substantial limitations. + +- must be the root element, because the `x:TypeArguments` attribute that must be used to specify the constrained type of the generic is only supported on the object element for the root element. + +- You must declare an `x:Class` attribute (which entails that the build action for this XAML file must be `Page` or some other build action that compiles the XAML). + +- is in a namespace and assembly that are not initially mapped to the default XML namespace. You must map a prefix for the namespace and assembly, and then use that prefix on the object element tag for . + +A more straightforward way to use capabilities from XAML in an application is to declare your own non-generic custom collection class that derives from , and constrains it to a specific type. Then map the assembly that contains this class, and reference it as an object element in your XAML. + + ]]> + diff --git a/xml/System.Linq.Expressions/BinaryExpression.xml b/xml/System.Linq.Expressions/BinaryExpression.xml index 0e737139903..5e43f397a84 100644 --- a/xml/System.Linq.Expressions/BinaryExpression.xml +++ b/xml/System.Linq.Expressions/BinaryExpression.xml @@ -53,7 +53,76 @@ Represents an expression that has a binary operator. - For more information about this API, see Supplemental API remarks for BinaryExpression. + + class represents an expression that has a binary operator. + +The following tables summarize the factory methods that can be used to create a that has a specific node type, represented by the property. Each table contains information for a specific class of operations such as arithmetic or bitwise. + +## Binary arithmetic operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| +||| +||| +||| +||| +||| +||| +||| +||| + +## Bitwise operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| +||| +||| + +## Shift operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| +||| + +## Conditional Boolean operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| +||| + +## Comparison operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| +||| +||| +||| +||| +||| + +## Coalescing operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| + +## Array indexing operations + +|Node Type|Factory Method| +|---------------|--------------------| +||| + +In addition, the methods can also be used to create a . These factory methods can be used to create a of any node type that represents a binary operation. The parameter of these methods that is of type specifies the desired node type. + + ]]> + object that represents the subtraction of one number from another. diff --git a/xml/System.Linq.Expressions/Expression.xml b/xml/System.Linq.Expressions/Expression.xml index 82221469d22..afb05ada36c 100644 --- a/xml/System.Linq.Expressions/Expression.xml +++ b/xml/System.Linq.Expressions/Expression.xml @@ -284,7 +284,37 @@ A to set the property equal to. Creates a that represents an arithmetic addition operation that does not have overflow checking. A that has the property equal to and the and properties set to the specified values. - For more information about this API, see Supplemental API remarks for Expression.Add. + + method returns a that has the property set to the implementing method. The property is set to the type of the node. If the node is lifted, the and properties are both `true`. Otherwise, they are `false`. The property is `null`. + +The following information describes the implementing method, the node type, and whether a node is lifted. + +## Implementing method + +The following rules determine the selected implementing method for the operation: + +- If the property of either `left` or `right` represents a user-defined type that overloads the addition operator, the that represents that method is the implementing method. +- Otherwise, if `left`.Type and `right`.Type are numeric types, the implementing method is `null`. + +## Node type and lifted versus non-lifted + +If the implementing method is not `null`: + +- If `left`.Type and `right`.Type are assignable to the corresponding argument types of the implementing method, the node is not lifted. The type of the node is the return type of the implementing method. +- If the following two conditions are satisfied, the node is lifted and the type of the node is the nullable type that corresponds to the return type of the implementing method: + + - `left`.Type and `right`.Type are both value types of which at least one is nullable and the corresponding non-nullable types are equal to the corresponding argument types of the implementing method. + - The return type of the implementing method is a non-nullable value type. + +If the implementing method is `null`: + +- If `left`.Type and `right`.Type are both non-nullable, the node is not lifted. The type of the node is the result type of the predefined addition operator. +- If `left`.Type and `right`.Type are both nullable, the node is lifted. The type of the node is the nullable type that corresponds to the result type of the predefined addition operator. + + ]]> + A to set the property equal to. Creates a that represents an arithmetic addition operation that does not have overflow checking. The implementing method can be specified. A that has the property equal to and the , and properties set to the specified values. - For more information about this API, see Supplemental API remarks for Expression.Add. + + method returns a that has the property set to the implementing method. The property is set to the type of the node. If the node is lifted, the and properties are both `true`. Otherwise, they are `false`. The property is `null`. + +The following information describes the implementing method, the node type, and whether a node is lifted. + +## Implementing method + +The following rules determine the selected implementing method for the operation: + +- If the property of either `left` or `right` represents a user-defined type that overloads the addition operator, the that represents that method is the implementing method. +- Otherwise, if `left`.Type and `right`.Type are numeric types, the implementing method is `null`. + +## Node type and lifted versus non-lifted + +If the implementing method is not `null`: + +- If `left`.Type and `right`.Type are assignable to the corresponding argument types of the implementing method, the node is not lifted. The type of the node is the return type of the implementing method. +- If the following two conditions are satisfied, the node is lifted and the type of the node is the nullable type that corresponds to the return type of the implementing method: + + - `left`.Type and `right`.Type are both value types of which at least one is nullable and the corresponding non-nullable types are equal to the corresponding argument types of the implementing method. + - The return type of the implementing method is a non-nullable value type. + +If the implementing method is `null`: + +- If `left`.Type and `right`.Type are both non-nullable, the node is not lifted. The type of the node is the result type of the predefined addition operator. +- If `left`.Type and `right`.Type are both nullable, the node is lifted. The type of the node is the nullable type that corresponds to the result type of the predefined addition operator. + + ]]> + or is . diff --git a/xml/System.Net.Http/HttpClient.xml b/xml/System.Net.Http/HttpClient.xml index a9a5f8735b8..df2d9d0d1ec 100644 --- a/xml/System.Net.Http/HttpClient.xml +++ b/xml/System.Net.Http/HttpClient.xml @@ -47,7 +47,147 @@ Provides a class for sending HTTP requests and receiving HTTP responses from a resource identified by a URI. - For more information about this API, see Supplemental API remarks for HttpClient. + + class instance acts as a session to send HTTP requests. An instance is a collection of settings applied to all requests executed by that instance. In addition, every instance uses its own connection pool, isolating its requests from requests executed by other instances. + +## Instancing + + is intended to be instantiated once and reused throughout the life of an application. In .NET Core and .NET 5+, `HttpClient` pools connections inside the handler instance and reuses a connection across multiple requests. If you instantiate an `HttpClient` class for every request, the number of sockets available under heavy loads will be exhausted. This exhaustion will result in errors. + +You can configure additional options by passing in a "handler", such as (or in .NET Core 2.1 or later), as part of the constructor. The connection properties on the handler cannot be changed once a request has been submitted, so one reason to create a new `HttpClient` instance would be if you need to change the connection properties. If different requests require different settings, this may also lead to an application having multiple instances, where each instance is configured appropriately, and then requests are issued on the relevant client. + +`HttpClient` only resolves DNS entries when a connection is created. It does not track any time to live (TTL) durations specified by the DNS server. If DNS entries change regularly, which can happen in some container scenarios, the client won't respect those updates. To solve this issue, you can limit the lifetime of the connection by setting the property, so that DNS lookup is required when the connection is replaced. + +```csharp +public class GoodController : ApiController +{ + private static readonly HttpClient httpClient; + + static GoodController() + { + var socketsHandler = new SocketsHttpHandler + { + PooledConnectionLifetime = TimeSpan.FromMinutes(2) + }; + + httpClient = new HttpClient(socketsHandler); + } +} +``` + +As an alternative to creating only one `HttpClient` instance, you can also use to manage the `HttpClient` instances for you. For more information, see [Guidelines for using HttpClient](/dotnet/fundamentals/networking/httpclient-guidelines). + +## Derivation + +The also acts as a base class for more specific HTTP clients. An example would be a `FacebookHttpClient` that provides additional methods specific to a Facebook web service (for example, a `GetFriends` method). Derived classes should not override the virtual methods on the class. Instead, use a constructor overload that accepts to configure any pre-request or post-request processing. + +## Transports + +The is a high-level API that wraps the lower-level functionality available on each platform where it runs. + +On each platform, tries to use the best available transport: + +| **Host/Runtime** | **Backend** | +| --------------------------- | ----------------------------------------------------------------------------------------- | +| Windows/.NET Framework | | +| Windows/Mono | | +| Windows/UWP | Windows native (HTTP 2.0 capable) | +| Windows/.NET Core 1.0-2.0 | Windows native (HTTP 2.0 capable) | +| macOS/Mono | | +| macOS/.NET Core 1.0-2.0 | `libcurl`-based HTTP transport (HTTP 2.0 capable) | +| Linux/Mono | | +| Linux/.NET Core 1.0-2.0 | `libcurl`-based HTTP transport (HTTP 2.0 capable) | +| .NET Core 2.1 and later | | + +Users can also configure a specific transport for by invoking the constructor that takes an . + +### .NET Framework & Mono + +By default on .NET Framework and Mono, is used to send requests to the server. This behavior can be modified by specifying a different handler in one of the constructor overloads with an parameter. If you require features like authentication or caching, you can use to configure settings and the instance can be passed to the constructor. The returned handler can be passed to a constructor overload that has an parameter. + +### .NET Core + +Starting with .NET Core 2.1, the class instead of provides the implementation used by higher-level HTTP networking classes such as . The use of offers a number of advantages: + +- A significant performance improvement when compared with the previous implementation. +- The elimination of platform dependencies, which simplifies deployment and servicing. For example, `libcurl` is no longer a dependency on .NET Core for macOS and .NET Core for Linux. +- Consistent behavior across all .NET platforms. + +If this change is undesirable, on Windows you can continue to use by referencing its [NuGet package](https://www.nuget.org/packages/System.Net.Http.WinHttpHandler/) and passing it to [HttpClient's constructor](xref:System.Net.Http.HttpClient.%23ctor(System.Net.Http.HttpMessageHandler)) manually. + +## Configure behavior using runtime configuration options + +Certain aspects of 's behavior are customizable through [Runtime configuration options](/dotnet/core/run-time-config/networking). However, the behavior of these switches differs through .NET versions. For example, in .NET Core 2.1 - 3.1, you can configure whether is used by default, but that option is no longer available starting in .NET 5. + +## Connection pooling + +`HttpClient` pools HTTP connections where possible and uses them for more than one request. This can have a significant performance benefit, especially for HTTPS requests, as the connection handshake is only done once. + +Connection pool properties can be configured on a or passed in during construction, including , , and . + +Disposing of the `HttpClient` instance closes the open connections and cancels any pending requests. + +> [!NOTE] +> If you concurrently send HTTP/1.1 requests to the same server, new connections can be created. Even if you reuse the `HttpClient` instance, if the rate of requests is high, or if there are any firewall limitations, that can exhaust the available sockets because of default TCP cleanup timers. To limit the number of concurrent connections, you can set the `MaxConnectionsPerServer` property. By default, the number of concurrent HTTP/1.1 connections is unlimited. + +## Buffering and request lifetime + +By default, `HttpClient` methods (except ) buffer the responses from the server, reading all the response body into memory before returning the async result. Those requests will continue until one of the following occurs: + +- The succeeds and returns a result. +- The is reached, in which case the will be cancelled. +- The passable to some method overloads is fired. +- is called. +- The HttpClient is disposed. + +You can change the buffering behavior on a per-request basis using the parameter available on some method overloads. This argument can be used to specify if the should be considered complete after reading just the response headers, or after reading and buffering the response content. + +If your app that uses and related classes in the namespace intends to download large amounts of data (50 megabytes or more), then the app should stream those downloads and not use the default buffering. If you use the default buffering, the client memory usage will get very large, potentially resulting in substantially reduced performance. + +## Thread safety + +The following methods are thread safe: + +- +- +- +- +- +- +- +- +- + +## Proxies + +By default, `HttpClient` reads proxy configuration from environment variables or user/system settings, depending on the platform. You can change this behavior by passing a or to, in order of precedence: + +- The property on an `HttpClientHandler` passed in during `HttpClient` construction +- The static property (affects all instances) + +You can disable the proxy using . The default configuration for Windows users is to try and detect a proxy using network discovery, which can be slow. For high throughput applications where it's known that a proxy isn't required, you should disable the proxy. + +Proxy settings (like ) should be changed only before the first request is made using the `HttpClient`. Changes made after using the `HttpClient` for the first time may not be reflected in subsequent requests. + +## Timeouts + +You can use to set a default timeout for all HTTP requests from the `HttpClient` instance. The timeout only applies to the xxxAsync methods that cause a request/response to be initiated. If the timeout is reached, the for that request is cancelled. + +You can set some additional timeouts if you pass in a instance when constructing the `HttpClient` object: + +| Property | Description | +| ------------ | -------------- | +| | Specifies a timeout that's used when a request requires a new TCP connection to be created. If the timeout occurs, the request is cancelled. | +| | Specifies a timeout to be used for each connection in the connection pool. If the connection is idle, the connection is immediately closed; otherwise, the connection is closed at the end of the current request. | +| | If a connection in the connection pool is idle for this long, the connection is closed. | +| | If request has an "Expect: 100-continue" header, it delays sending content until the timeout or until a "100-continue" response is received. | + +`HttpClient` only resolves DNS entries when the connections are created. It does not track any time to live (TTL) durations specified by the DNS server. If DNS entries are changing regularly, which can happen in some container scenarios, you can use the to limit the lifetime of the connection so that DNS lookup is required when replacing the connection. + + ]]> + The default message handler used by in .NET Framework. - For more information about this API, see Supplemental API remarks for HttpClientHandler. + + class and classes derived from it enable developers to configure a variety of options ranging from proxies to authentication. + +## HttpClientHandler in .NET Core + +Starting in .NET Core 2.1, the implementation of the `HttpClientHandler` class was changed to be based on the cross-platform HTTP protocol stack used by the class. Prior to .NET Core 2.1, the `HttpClientHandler` class used older HTTP protocol stacks ( on Windows and `CurlHandler`, an internal class implemented on top of Linux's native `libcurl` component, on Linux). + + ]]> + Implements the Berkeley sockets interface. - For more information about this API, see Supplemental API remarks for Socket. + + class provides a rich set of methods and properties for network communications. The class allows you to perform both synchronous and asynchronous data transfer using any of the communication protocols listed in the enumeration. + +The class follows the .NET naming pattern for asynchronous methods. For example, the synchronous method corresponds to the asynchronous variants. + +Use the following methods for synchronous operation mode: + +- If you are using a connection-oriented protocol such as TCP, your server can listen for connections using the method. The method processes any incoming connection requests and returns a that you can use to communicate data with the remote host. Use this returned to call the or method. Call the method prior to calling the method if you want to specify the local IP address and port number. Use a port number of zero if you want the underlying service provider to assign a free port for you. If you want to connect to a listening host, call the method. To communicate data, call the or method. +- If you are using a connectionless protocol such as UDP, you do not need to listen for connections at all. Call the method to accept any incoming datagrams. Use the method to send datagrams to a remote host. + +To process communications asynchronously, use the following methods: + +- If you are using a connection-oriented protocol such as TCP, use to connect with a listening host. Use or to communicate data asynchronously. Incoming connection requests can be processed using . +- If you are using a connectionless protocol such as UDP, you can use to send datagrams, and to receive datagrams. + +If you perform multiple asynchronous operations on a socket, they do not necessarily complete in the order in which they are started. + +When you are finished sending and receiving data, use the method to disable the . After calling , call the method to release all resources associated with the . + +The class allows you to configure your using the method. Retrieve these settings using the method. + + ]]> + class can be used to send data to an HTTP server, printing the ASCII response to the standard output. This example blocks the calling thread until the entire page is received. diff --git a/xml/System.Net/FtpWebRequest.xml b/xml/System.Net/FtpWebRequest.xml index a9e8e650883..4f51a56ec69 100644 --- a/xml/System.Net/FtpWebRequest.xml +++ b/xml/System.Net/FtpWebRequest.xml @@ -1456,9 +1456,17 @@ > [!NOTE] > This property is not supported, and setting it has no effect. Getting the property value returns `null`. -For more information about this API, see [Supplemental API remarks for System.Net.FtpWebRequest.Proxy](/dotnet/fundamentals/runtime-libraries/system-net-ftpwebrequest-proxy). +> [!NOTE] +> This property is not supported on .NET Core, and setting it has no effect. Getting the property value returns `null`. + +The property identifies the instance that communicates with the FTP server. The proxy is set by the system by using configuration files and the Local Area Network settings. To specify that no proxy should be used, set to the proxy instance returned by the method. For more information about automatic proxy detection, see [Automatic Proxy Detection](/dotnet/framework/network-programming/automatic-proxy-detection). + +You must set before writing data to the request's stream or getting the response. Changing after calling the , , , or method causes an exception. + +The class supports HTTP and ISA Firewall Client proxies. - ]]> +If the specified proxy is an HTTP proxy, only the , , and commands are supported. +]]> This property cannot be set to . A new value was specified for this property for a request that is already in progress. diff --git a/xml/System.Net/HttpListener.xml b/xml/System.Net/HttpListener.xml index 6956a0f232e..0473239cec4 100644 --- a/xml/System.Net/HttpListener.xml +++ b/xml/System.Net/HttpListener.xml @@ -54,7 +54,55 @@ Provides a simple, programmatically controlled HTTP protocol listener. This class cannot be inherited. - For more information about this API, see Supplemental API remarks for HttpListener. + + class, you can create a simple HTTP protocol listener that responds to HTTP requests. The listener is active for the lifetime of the object and runs within your application with its permissions. + +To use , create a new instance of the class using the constructor and use the property to gain access to the collection that holds the strings that specify which Uniform Resource Identifier (URI) prefixes the should process. + +A URI prefix string is composed of a scheme (http or https), a host, an optional port, and an optional path. An example of a complete prefix string is `http://www.contoso.com:8080/customerData/`. Prefixes must end in a forward slash ("/"). The object with the prefix that most closely matches a requested URI responds to the request. Multiple objects cannot add the same prefix; a exception is thrown if a adds a prefix that is already in use. + +When a port is specified, the host element can be replaced with "\*" to indicate that the accepts requests sent to the port if the requested URI does not match any other prefix. For example, to receive all requests sent to port 8080 when the requested URI is not handled by any , the prefix is *http://\*:8080/*. Similarly, to specify that the accepts all requests sent to a port, replace the host element with the "+" character. For example, *https://+:8080*. The "\*" and "+" characters can be present in prefixes that include paths. + +Wildcard subdomains are supported in URI prefixes that are managed by an object. To specify a wildcard subdomain, use the "\*" character as part of the hostname in a URI prefix. For example, *http://\*.foo.com/*. Pass this as the argument to the method. + +> [!WARNING] +> Top-level wildcard bindings (*http://\*:8080/* and *http://+:8080*) should **not** be used. Top-level wildcard bindings can open up your app to security vulnerabilities. This applies to both strong and weak wildcards. Use explicit host names rather than wildcards. Subdomain wildcard binding (for example, `*.mysub.com`) doesn't have this security risk if you control the entire parent domain (as opposed to `*.com`, which is vulnerable). See [rfc7230 section-5.4](https://tools.ietf.org/html/rfc7230#section-5.4) for more information. + +To begin listening for requests from clients, add the URI prefixes to the collection and call the method. offers both synchronous and asynchronous models for processing client requests. Requests and their associated responses are accessed using the object returned by the method or its asynchronous counterparts, the and methods. + +The synchronous model is appropriate if your application should block while waiting for a client request and if you want to process only one request at a time. Using the synchronous model, call the method, which waits for a client to send a request. The method returns an object to you for processing when one occurs. + +In the more complex asynchronous model, your application does not block while waiting for requests and each request is processed in its own execution thread. Use the method to specify an application-defined method to be called for each incoming request. Within that method, call the method to obtain the request, process it, and respond. + +In either model, incoming requests are accessed using the property and are represented by objects. Similarly, responses are accessed using the property and are represented by objects. These objects share some functionality with the and objects, but the latter objects cannot be used in conjunction with because they implement client, not server, behaviors. + +An can require client authentication. You can either specify a particular scheme to use for authentication, or you can specify a delegate that determines the scheme to use. You must require some form of authentication to obtain information about the client's identity. For additional information, see the , , and properties. + +> [!NOTE] +> If you create an using https, you must select a Server Certificate for that listener. Otherwise, requests to this will fail with an unexpected close of the connection. + +> [!NOTE] +> You can configure Server Certificates and other listener options by using Network Shell (netsh.exe). See [Network Shell (Netsh)](/windows-server/networking/technologies/netsh/netsh) for more details. The executable began shipping with Windows Server 2008 and Windows Vista. + +> [!NOTE] +> If you specify multiple authentication schemes for the , the listener will challenge clients in the following order: `Negotiate`, `NTLM`, `Digest`, and then `Basic`. + +## HTTP.sys + +The class is built on top of `HTTP.sys`, which is the kernel mode listener that handles all HTTP traffic for Windows. +`HTTP.sys` provides connection management, bandwidth throttling, and web server logging. +Use the [HttpCfg.exe](/windows/win32/http/httpcfg-exe) tool to add SSL certificates. + +Starting in .NET 11, the Windows `HTTP.sys` implementation of supports enabling kernel-level response buffering. When enabled, response data is buffered by `HTTP.sys` before being sent to the client, which can improve throughput for high-latency connections. This can be enabled by calling the method as follows: + + ```csharp + AppContext.SetSwitch("System.Net.HttpListener.EnableKernelResponseBuffering", true); + ``` + + ]]> + Represents an arbitrarily large signed integer. - For more information about this API, see Supplemental API remarks for BigInteger. + + type is an immutable type that represents an arbitrarily large integer whose value in theory has no upper or lower bounds. The members of the type closely parallel those of other integral types (the , , , , , , , and types). This type differs from the other integral types in .NET, which have a range indicated by their `MinValue` and `MaxValue` properties. + +> [!NOTE] +> Because the type is immutable (see [Mutability](#mutability)) and because it has no upper or lower bounds, an can be thrown for any operation that causes a value to grow too large. + +## Instantiate a BigInteger object + +You can instantiate a object in several ways: + +- You can use the `new` keyword and provide any integral or floating-point value as a parameter to the constructor. (Floating-point values are truncated before they are assigned to the .) The following example illustrates how to use the `new` keyword to instantiate values. + + :::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs" id="Snippet1"::: + :::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb" id="Snippet1"::: + +- You can declare a variable and assign it a value just as you would any numeric type, as long as that value is an integral type. The following example uses assignment to create a value from an . + + :::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs" id="Snippet2"::: + :::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb" id="Snippet2"::: + +- You can assign a decimal or floating-point value to a object if you cast the value or convert it first. The following example explicitly casts (in C#) or converts (in Visual Basic) a and a value to a . + + :::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs" id="Snippet3"::: + :::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb" id="Snippet3"::: + +These methods enable you to instantiate a object whose value is in the range of one of the existing numeric types only. You can instantiate a object whose value can exceed the range of the existing numeric types in one of three ways: + +- You can use the `new` keyword and provide a byte array of any size to the constructor. For example: + + :::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs" id="Snippet4"::: + :::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb" id="Snippet4"::: + +- You can call the or methods to convert the string representation of a number to a . For example: + + :::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs" id="Snippet5"::: + :::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb" id="Snippet5"::: + +- You can call a `static` (`Shared` in Visual Basic) method that performs some operation on a numeric expression and returns a calculated result. The following example does this by cubing and assigning the result to a . + + :::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/BigInteger_Examples.cs" id="Snippet6"::: + :::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/BigInteger_Examples.vb" id="Snippet6"::: + +The uninitialized value of a is . + +## Perform operations on BigInteger values + +You can use a instance as you would use any other integral type. overloads the standard numeric operators to enable you to perform basic mathematical operations such as addition, subtraction, division, multiplication, and unary negation. You can also use the standard numeric operators to compare two values with each other. Like the other integral types, also supports the bitwise `And`, `Or`, `XOr`, left shift, and right shift operators. For languages that do not support custom operators, the structure also provides equivalent methods for performing mathematical operations. These include , , , , , and several others. + +Many members of the structure correspond directly to members of the other integral types. In addition, adds members such as the following: + +- , which returns a value that indicates the sign of a value. + +- , which returns the absolute value of a value. + +- , which returns both the quotient and remainder of a division operation. + +- , which returns the greatest common divisor of two values. + +Many of these additional members correspond to the members of the class, which provides the functionality to work with the primitive numeric types. + +## Mutability + +The following example instantiates a object and then increments its value by one. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs" id="Snippet1"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb" id="Snippet1"::: + +Although this example appears to modify the value of the existing object, this is not the case. objects are immutable, which means that internally, the common language runtime actually creates a new object and assigns it a value one greater than its previous value. This new object is then returned to the caller. + +> [!NOTE] +> The other numeric types in .NET are also immutable. However, because the type has no upper or lower bounds, its values can grow extremely large and have a measurable impact on performance. + +Although this process is transparent to the caller, it does incur a performance penalty. In some cases, especially when repeated operations are performed in a loop on very large values, that performance penalty can be significant. For example, in the following example, an operation is performed repetitively up to a million times, and a value is incremented by one every time the operation succeeds. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs" id="Snippet12"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb" id="Snippet12"::: + +In such a case, you can improve performance by performing all intermediate assignments to an variable. The final value of the variable can then be assigned to the object when the loop exits. The following example provides an illustration. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/Mutability_Examples.cs" id="Snippet3"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/Mutability_Examples.vb" id="Snippet3"::: + +## Byte arrays and hexadecimal strings + +If you convert values to byte arrays, or if you convert byte arrays to values, you must consider the order of bytes. The structure expects the individual bytes in a byte array to appear in little-endian order (that is, the lower-order bytes of the value precede the higher-order bytes). You can round-trip a value by calling the method and then passing the resulting byte array to the constructor, as the following example shows. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs" id="Snippet1"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb" id="Snippet1"::: + +To instantiate a value from a byte array that represents a value of some other integral type, you can pass the integral value to the method, and then pass the resulting byte array to the constructor. The following example instantiates a value from a byte array that represents an value. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs" id="Snippet2"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb" id="Snippet2"::: + +The structure assumes that negative values are stored by using two's complement representation. Because the structure represents a numeric value with no fixed length, the constructor always interprets the most significant bit of the last byte in the array as a sign bit. To prevent the constructor from confusing the two's complement representation of a negative value with the sign and magnitude representation of a positive value, positive values in which the most significant bit of the last byte in the byte array would ordinarily be set should include an additional byte whose value is 0. For example, 0xC0 0xBD 0xF0 0xFF is the little-endian hexadecimal representation of either -1,000,000 or 4,293,967,296. Because the most significant bit of the last byte in this array is on, the value of the byte array would be interpreted by the constructor as -1,000,000. To instantiate a whose value is positive, a byte array whose elements are 0xC0 0xBD 0xF0 0xFF 0x00 must be passed to the constructor. The following example illustrates this. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs" id="Snippet3"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb" id="Snippet3"::: + +Byte arrays created by the method from positive values include this extra zero-value byte. Therefore, the structure can successfully round-trip values by assigning them to, and then restoring them from, byte arrays, as the following example shows. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs" id="Snippet4"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb" id="Snippet4"::: + +However, you may need to add this additional zero-value byte to byte arrays that are created dynamically by the developer or that are returned by methods that convert unsigned integers to byte arrays (such as , , and ). + +When parsing a hexadecimal string, the and methods assume that if the most significant bit of the first byte in the string is set, or if the first hexadecimal digit of the string represents the lower four bits of a byte value, the value is represented by using two's complement representation. For example, both "FF01" and "F01" represent the decimal value -255. To differentiate positive from negative values, positive values should include a leading zero. The relevant overloads of the method, when they are passed the "X" format string, add a leading zero to the returned hexadecimal string for positive values. This makes it possible to round-trip values by using the and methods, as the following example shows. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.cs" id="Snippet5"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples.vb" id="Snippet5"::: + +However, the hexadecimal strings created by calling the `ToString` methods of the other integral types or the overloads of the method that include a `toBase` parameter do not indicate the sign of the value or the source data type from which the hexadecimal string was derived. Successfully instantiating a value from such a string requires some additional logic. The following example provides one possible implementation. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.cs" id="Snippet6"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/BigInteger/Overview/ByteAndHex_Examples2.vb" id="Snippet6"::: + + ]]> + diff --git a/xml/System.Numerics/Complex.xml b/xml/System.Numerics/Complex.xml index fb9528666ac..64c0d6a21c4 100644 --- a/xml/System.Numerics/Complex.xml +++ b/xml/System.Numerics/Complex.xml @@ -172,7 +172,100 @@ Represents a complex number. - For more information about this API, see Supplemental API remarks for Complex. + + 2 = -1. The real part of the complex number is represented by *x*, and the imaginary part of the complex number is represented by *y*. + +The type uses the Cartesian coordinate system (real, imaginary) when instantiating and manipulating complex numbers. A complex number can be represented as a point in a two-dimensional coordinate system, which is known as the complex plane. The real part of the complex number is positioned on the x-axis (the horizontal axis), and the imaginary part is positioned on the y-axis (the vertical axis). + +Any point in the complex plane can also be expressed based on its absolute value, by using the polar coordinate system. In polar coordinates, a point is characterized by two numbers: + +- Its magnitude, which is the distance of the point from the origin (that is, 0,0, or the point at which the x-axis and the y-axis intersect). +- Its phase, which is the angle between the real axis and the line drawn from the origin to the point. + +## Instantiate a complex number + +You can assign a value to a complex number in one of the following ways: + +- By passing two values to its constructor. The first value represents the real part of the complex number, and the second value represents its imaginary part. These values represent the position of the complex number in the two-dimensional Cartesian coordinate system. + +- By calling the static (`Shared` in Visual Basic) method to create a complex number from its polar coordinates. + +- By assigning a , , , , , , , , , or value to a object. The value becomes the real part of the complex number, and its imaginary part equals 0. + +- By casting (in C#) or converting (in Visual Basic) a or value to a object. The value becomes the real part of the complex number, and its imaginary part equals 0. + +- By assigning the complex number that is returned by a method or operator to a object. For example, is a static method that returns a complex number that is the sum of two complex numbers, and the operator adds two complex numbers and returns the result. + +The following example demonstrates each of these five ways of assigning a value to a complex number. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/Complex/Overview/create1.cs" id="Snippet2"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/Complex/Overview/create1.vb" id="Snippet2"::: + +## Operations with complex numbers + +The structure in .NET includes members that provide the following functionality: + +- Methods to compare two complex numbers to determine whether they are equal. +- Operators to perform arithmetic operations on complex numbers. operators enable you to perform addition, subtraction, multiplication, division, and unary negation with complex numbers. +- Methods to perform other numerical operations on complex numbers. In addition to the four basic arithmetic operations, you can raise a complex number to a specified power, find the square root of a complex number, and get the absolute value of a complex number. +- Methods to perform trigonometric operations on complex numbers. For example, you can calculate the tangent of an angle represented by a complex number. + +Note that, because the and properties are read-only, you cannot modify the value of an existing object. All methods that perform an operation on a number, if their return value is of type , return a new number. + +## Precision and complex numbers + +The real and imaginary parts of a complex number are represented by two double-precision floating-point values. This means that values, like double-precision floating-point values, can lose precision as a result of numerical operations. This means that strict comparisons for equality of two values may fail, even if the difference between the two values is due to a loss of precision. For more information, see . + +For example, performing exponentiation on the logarithm of a number should return the original number. However, in some cases, the loss of precision of floating-point values can cause slight differences between the two values, as the following example illustrates. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/Complex/Overview/precision1.cs" id="Snippet5"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/Complex/Overview/precision1.vb" id="Snippet5"::: + +Similarly, the following example, which calculates the square root of a number, produces slightly different results on the 32-bit and IA64 versions of .NET. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/Complex/Overview/precision1.cs" id="Snippet6"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/Complex/Overview/precision1.vb" id="Snippet6"::: + +## Infinity and NaN + +The real and imaginary parts of a complex number are represented by values. In addition to ranging from to , the real or imaginary part of a complex number can have a value of , , or . , , and all propagate in any arithmetic or trigonometric operation. + +In the following example, division by produces a complex number whose real and imaginary parts are both . As a result, performing multiplication with this value also produces a complex number whose real and imaginary parts are . Similarly, performing a multiplication that overflows the range of the type produces a complex number whose real part is and whose imaginary part is . Subsequently performing division with this complex number returns a complex number whose real part is and whose imaginary part is . + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/Complex/Overview/nan1.cs" id="Snippet3"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/Complex/Overview/nan1.vb" id="Snippet3"::: + +Mathematical operations with complex numbers that are invalid or that overflow the range of the data type do not throw an exception. Instead, they return a , , or under the following conditions: + +- The division of a positive number by zero returns . +- Any operation that overflows the upper bound of the data type returns . +- The division of a negative number by zero returns . +- Any operation that overflows the lower bound of the data type returns . +- The division of a zero by zero returns . +- Any operation that is performed on operands whose values are , , or returns , , or , depending on the specific operation. + +Note that this applies to any intermediate calculations performed by a method. For example, the multiplication of `new Complex(9e308, 9e308) and new Complex(2.5, 3.5)` uses the formula (ac - bd) + (ad + bc)i. The calculation of the real component that results from the multiplication evaluates the expression 9e308 *2.5 - 9e308* 3.5. Each intermediate multiplication in this expression returns , and the attempt to subtract from returns . + +## Format a complex number + +By default, the string representation of a complex number takes the form `<`*real*`;` *imaginary*`>`, where *real* and *imaginary* are the string representations of the values that form the complex number's real and imaginary components. Some overloads of the method allow customization of the string representations of these values to reflect the formatting conventions of a particular culture or to appear in a particular format defined by a standard or custom numeric format string. (For more information, see [Standard Numeric Format Strings](/dotnet/standard/base-types/standard-numeric-format-strings) and [Custom Numeric Format Strings](/dotnet/standard/base-types/custom-numeric-format-strings).) + +One of the more common ways of expressing the string representation of a complex number takes the form `a + bi`, where `a` is the complex number's real component, and `b` is the complex number's imaginary component. In electrical engineering, a complex number is most commonly expressed as `a + bj`. You can return the string representation of a complex number in either of these two forms. To do this, define a custom format provider by implementing the and interfaces, and then call the method. + +The following example defines a `ComplexFormatter` class that represents a complex number as a string in the form of either `a + bi` or `a + bj`. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/Complex/Overview/customfmt1.cs" id="Snippet1"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/Complex/Overview/customfmt1.vb" id="Snippet1"::: + +The following example then uses this custom formatter to display the string representation of a complex number. + +:::code language="csharp" source="~/snippets/csharp/System.Numerics/Complex/Overview/customfmt1.cs" id="Snippet4"::: +:::code language="vb" source="~/snippets/visualbasic/System.Numerics/Complex/Overview/customfmt1.vb" id="Snippet4"::: + + ]]> + diff --git a/xml/System.Security.Cryptography.Xml/SignedXml.xml b/xml/System.Security.Cryptography.Xml/SignedXml.xml index 0a4e8d28abb..2cf6736bebd 100644 --- a/xml/System.Security.Cryptography.Xml/SignedXml.xml +++ b/xml/System.Security.Cryptography.Xml/SignedXml.xml @@ -39,7 +39,151 @@ Provides a wrapper on a core XML signature object to facilitate creating XML signatures. - For more information about this API, see Supplemental API remarks for SignedXml. + + class is the .NET implementation of the World Wide Web Consortium (W3C) [XML Signature Syntax and Processing Specification](https://www.w3.org/TR/xmldsig-core/), also known as XMLDSIG (XML Digital Signature). XMLDSIG is a standards-based, interoperable way to sign and verify all or part of an XML document or other data that is addressable from a Uniform Resource Identifier (URI). + +Use the class whenever you need to share signed XML data between applications or organizations in a standard way. Any data signed using this class can be verified by any conforming implementation of the W3C specification for XMLDSIG. + +The class allows you to create the following three kinds of XML digital signatures: + +| Signature Type | Description | +|----------------------|-----------------------------------------------------------------| +| Enveloped signature | The signature is contained within the XML element being signed. | +| Enveloping signature | The signed XML is contained within the `` element. | +| Internal detached signature | The signature and signed XML are in the same document, but neither element contains the other. | + +There is also a fourth kind of signature called an external detached signature which is when the data and signature are in separate XML documents. External detached signatures are not supported by the class. + +## Structure of an XML signature + +XMLDSIG creates a `` element, which contains a digital signature of an XML document or other data that is addressable from a URI. The `` element can optionally contain information about where to find a key that will verify the signature and which cryptographic algorithm was used for signing. The basic structure is as follows: + +```xml + + + + + + + + + + Base64EncodedValue== + + + AnotherBase64EncodedValue=== + +``` + +The main parts of this structure are: + +- The `` element + + Specifies the rules for rewriting the `Signature` element from XML/text into bytes for signature validation. The default value in .NET is , which identifies a trustworthy algorithm. This element is represented by the property. + +- The `` element + + Specifies the algorithm used for signature generation and validation, which was applied to the `` element to produce the value in ``. In the previous example, the value identifies an RSA PKCS1 SHA-1 signature. Due to collision problems with SHA-1, Microsoft recommends a security model based on SHA-256 or better. This element is represented by the property. + +- The `` element + + Specifies the cryptographic signature for the `` element. If this signature does not verify, then some portion of the `` block was tampered with, and the document is considered invalid. As long as the `` value is trustworthy, this value is highly resistant to tampering. This element is represented by the property. + +- The `URI` attribute of the `` element + + Specifies a data object using a URI reference. This attribute is represented by the property. + + - Not specifying the `URI` attribute, that is, setting the property to `null`, means that the receiving application is expected to know the identity of the object. In most cases, a `null` URI will result in an exception being thrown. Do not use a `null` URI, unless your application is interoperating with a protocol which requires it. + + - Setting the `URI` attribute to an empty string indicates that the root element of the document is being signed, a form of enveloped signature. + + - If the value of `URI` attribute starts with #, then the value must resolve to an element in the current document. This form can be used with any of the supported signature types (enveloped signature, enveloping signature or internal detached signature). + + - Anything else is considered an external resource detached signature and is not supported by the class. + +- The `` element + + Contains an ordered list of `` elements that describe how the signer obtained the data object that was digested. A transform algorithm is similar to the canonicalization method, but instead of rewriting the `` element, it rewrites the content identified by the `URI` attribute of the `` element. The `` element is represented by the class. + + - Each transform algorithm is defined as taking either XML (an XPath node-set) or bytes as input. If the format of the current data differs from the transform input requirements, conversion rules are applied. + + - Each transform algorithm is defined as producing either XML or bytes as the output. + + - If the output of the last transform algorithm is not defined in bytes (or no transforms were specified), then the [canonicalization method](https://www.w3.org/TR/2001/REC-xml-c14n-20010315) is used as an implicit transform (even if a different algorithm was specified in the `` element). + + - A value of for the transform algorithm encodes a rule which is interpreted as remove the `` element from the document. Otherwise, a verifier of an enveloped signature will digest the document, including the signature, but the signer would have digested the document before the signature was applied, leading to different answers. + +- The `` element + + Identifies the digest (cryptographic hash) method to apply on the transformed content identified by the `URI` attribute of the `` element. This is represented by the property. + +## Choosing a canonicalization method + +Unless interoperating with a specification which requires the use of a different value, we recommend that you use the default .NET canonicalization method, which is the XML-C14N 1.0 algorithm, whose value is . The XML-C14N 1.0 algorithm is required to be supported by all implementations of XMLDSIG, particularly as it is an implicit final transform to apply. + +There are versions of canonicalization algorithms which support preserving comments. Comment-preserving canonicalization methods are not recommended because they violate the "sign what is seen" principle. That is, the comments in a `` element will not alter the processing logic for how the signature is performed, merely what the signature value is. When combined with a weak signature algorithm, allowing the comments to be included gives an attacker unnecessary freedom to force a hash collision, making a tampered document appear legitimate. In .NET Framework, only built-in canonicalizers are supported by default. To support additional or custom canonicalizers, see the property. If the document uses a canonicalization method that is not in the collection represented by the property, then the method will return `false`. + +> [!NOTE] +> An extremely defensive application can remove any values it does not expect signers to use from the collection. + +## Are the reference values safe from tampering? + +Yes, the `` values are safe from tampering. .NET verifies the `` computation before processing any of the `` values and their associated transforms, and will abort early to avoid potentially malicious processing instructions. + +## Choose the elements to sign + +We recommend that you use the value of "" for the `URI` attribute (or set the property to an empty string), if possible. This means the whole document is considered for the digest computation, which means the whole document is protected from tampering. + +It is very common to see `URI` values in the form of anchors such as #foo, referring to an element whose ID attribute is "foo". Unfortunately, it is easy for this to be tampered with because this includes only the content of the target element, not the context. Abusing this distinction is known as XML Signature Wrapping (XSW). + +If your application considers comments to be semantic (which is not common when dealing with XML), then you should use "#xpointer(/)" instead of "", and "#xpointer(id('foo'))" instead of "#foo". The #xpointer versions are interpreted as including comments, while the shortname forms are excluding comments. + +If you need to accept documents which are only partially protected and you want to ensure that you are reading the same content that the signature protected, use the method. + +## Security considerations about the KeyInfo element + +The data in the optional `` element (that is, the property), which contains a key to validate the signature, should not be trusted. + +In particular, when the value represents a bare RSA, DSA or ECDSA public key, the document could have been tampered with, despite the method reporting that the signature is valid. This can happen because the entity doing the tampering just has to generate a new key and re-sign the tampered document with that new key. So, unless your application verifies that the public key is an expected value, the document should be treated as if it were tampered with. This requires that your application examine the public key embedded within the document and verify it against a list of known values for the document context. For example, if the document could be understood to be issued by a known user, you'd check the key against a list of known keys used by that user. + +You can also verify the key after processing the document by using the method, instead of using the method. But, for the optimal security, you should verify the key beforehand. + +Alternately, consider trying the user's registered public keys, rather than reading what's in the `` element. + +## Security considerations about the X509Data element + +The optional `` element is a child of the `` element and contains one or more X509 certificates or identifiers for X509 certificates. The data in the `` element should also not be inherently trusted. + +When verifying a document with the embedded `` element, .NET verifies only that the data resolves to an X509 certificate whose public key can be successfully used to validate the document signature. Unlike calling the method with the `verifySignatureOnly` parameter set to `false`, no revocation check is performed, no chain trust is checked, and no expiration is verified. Even if your application extracts the certificate itself and passes it to the method with the `verifySignatureOnly` parameter set to `false`, that is still not sufficient validation to prevent document tampering. The certificate still needs to be verified as being appropriate for the document being signed. + +Using an embedded signing certificate can provide useful key rotation strategies, whether in the `` section or in the document content. When using this approach an application should extract the certificate manually and perform validation similar to: + +- The certificate was issued directly or via a chain by a Certificate Authority (CA) whose public certificate is embedded in the application. + + Using the OS-provided trust list without additional checks, such as a known subject name, is not sufficient to prevent tampering in . + +- The certificate is verified to have not been expired at the time of document signing (or "now" for near real-time document processing). + +- For long-lived certificates issued by a CA which supports revocation, verify the certificate was not revoked. + +- The certificate subject is verified as being appropriate to the current document. + +## Choosing the transform algorithm + +If you are interoperating with a specification which has dictated specific values (such as XrML), then you need to follow the specification. If you have an enveloped signature (such as when signing the whole document), then you need to use (represented by the class). You can specify the implicit XML-C14N transform as well, but it's not necessary. For an enveloping or detached signature, no transforms are required. The implicit XML-C14N transform takes care of everything. + +With the security updated introduced by the [Microsoft Security Bulletin MS16-035](/security-updates/securitybulletins/2016/ms16-035), .NET has restricted what transforms can be used in document verification by default, with untrusted transforms causing to always return `false`. In particular, transforms which require additional input (specified as child elements in the XML) are no longer allowed due to their susceptibility of abuse by malicious users. The W3C advises avoiding the XPath and XSLT transforms, which are the two main transforms affected by these restrictions. + +## The problem with external references + +If an application does not verify that external references seem appropriate for the current context, they can be abused in ways that provide for many security vulnerabilities (including Denial of Service, Distributed Reflection Denial of Service, Information Disclosure, Signature Bypass, and Remote Code Execution). Even if an application were to validate the external reference URI, there would remain a problem of the resource being loaded twice: once when your application reads it, and once when reads it. Since there's no guarantee that the application read and document verify steps have the same content, the signature does not provide trustworthiness. + +Given the risks of external references, will throw an exception when an external reference is encountered. For more information about this issue, see [.NET Framework applications encounter exception errors](https://support.microsoft.com/topic/after-you-apply-security-update-3141780-net-framework-applications-encounter-exception-errors-or-unexpected-failures-while-processing-files-that-contain-signedxml-922edd45-a91e-c755-bb30-2604acf37362). + + ]]> + Performs asymmetric encryption and decryption using the implementation of the algorithm provided by the cryptographic service provider (CSP). This class cannot be inherited. - For more information about this API, see Supplemental API remarks for RSACryptoServiceProvider. + + class is the default implementation of . + +The supports key sizes from 384 bits to 16384 bits in increments of 8 bits if you have the Microsoft Enhanced Cryptographic Provider installed. It supports key sizes from 384 bits to 512 bits in increments of 8 bits if you have the Microsoft Base Cryptographic Provider installed. + +Valid key sizes are dependent on the cryptographic service provider (CSP) that is used by the instance. Windows CSPs enable keys sizes of 384 to 16384 bits for Windows versions prior to Windows 8.1, and key sizes of 512 to 16384 bits for Windows 8.1. For more information, see [CryptGenKey](/windows/win32/api/wincrypt/nf-wincrypt-cryptgenkey) function in the Windows documentation. + +## Interoperation with the Microsoft Cryptographic API (CAPI) + +Unlike the RSA implementation in unmanaged CAPI, the class reverses the order of an encrypted array of bytes after encryption and before decryption. By default, data encrypted by the class cannot be decrypted by the CAPI `CryptDecrypt` function and data encrypted by the CAPI `CryptEncrypt` method cannot be decrypted by the class. + +If you do not compensate for the reverse ordering when interoperating between APIs, the class throws a . + +To interoperate with CAPI, you must manually reverse the order of encrypted bytes before the encrypted data interoperates with another API. You can easily reverse the order of a managed byte array by calling the method. + + ]]> + class to encrypt a string into an array of bytes and then decrypt the bytes back into a string. diff --git a/xml/System.Security.Cryptography/RSAParameters.xml b/xml/System.Security.Cryptography/RSAParameters.xml index c3e8a4d20e4..43ed8c06fa2 100644 --- a/xml/System.Security.Cryptography/RSAParameters.xml +++ b/xml/System.Security.Cryptography/RSAParameters.xml @@ -62,7 +62,50 @@ Represents the standard parameters for the algorithm. - For more information about this API, see Supplemental API remarks for RSAParameters. + + structure represents the standard parameters for the RSA algorithm. + +The class exposes an method that enables you to retrieve the raw RSA key in the form of an structure. + +To understand the contents of this structure, it helps to be familiar with how the algorithm works. The next section discusses the algorithm briefly. + +## RSA algorithm + +To generate a key pair, you start by creating two large prime numbers named p and q. These numbers are multiplied and the result is called n. Because p and q are both prime numbers, the only factors of n are 1, p, q, and n. + +If we consider only numbers that are less than n, the count of numbers that are relatively prime to n, that is, have no factors in common with n, equals (p - 1)(q - 1). + +Now you choose a number e, which is relatively prime to the value you calculated. The public key is now represented as {e, n}. + +To create the private key, you must calculate d, which is a number such that (d)(e) mod (p - 1)(q - 1) = 1. In accordance with the Euclidean algorithm, the private key is now {d, n}. + +Encryption of plaintext m to ciphertext c is defined as c = (m ^ e) mod n. Decryption would then be defined as m = (c ^ d) mod n. + +## Summary of fields + +Section A.1.2 of the [PKCS #1: RSA Cryptography Standard](https://datatracker.ietf.org/doc/html/rfc8017#appendix-A.1.2) defines a format for RSA private keys. + +The following table summarizes the fields of the structure. The third column provides the corresponding field in section A.1.2 of [PKCS #1: RSA Cryptography Standard](https://datatracker.ietf.org/doc/html/rfc8017#appendix-A.1.2). + +| field | Contains | Corresponding PKCS #1 field | +| ---------------------------------------------------------- | ----------------------- | --------------------------- | +| | d, the private exponent | privateExponent | +| | d mod (p - 1) | exponent1 | +| | d mod (q - 1) | exponent2 | +| | e, the public exponent | publicExponent | +| | (InverseQ)(q) = 1 mod p | coefficient | +| | n | modulus | +| | p | prime1 | +| | q | prime2 | + +The security of RSA derives from the fact that, given the public key { e, n }, it is computationally infeasible to calculate d, either directly or by factoring n into p and q. Therefore, any part of the key related to d, p, or q must be kept secret. If you call and ask for only the public key information, this is why you will receive only and . The other fields are available only if you have access to the private key, and you request it. + + is not encrypted in any way, so you must be careful when you use it with the private key information. All members of are serialized. If anyone can derive or intercept the private key parameters, the key and all the information encrypted or signed with it are compromised. + + ]]> + Cryptographic Services All About RSAParameters (blog post) diff --git a/xml/System.Security/SecureString.xml b/xml/System.Security/SecureString.xml index 43c9b50726f..a951523b549 100644 --- a/xml/System.Security/SecureString.xml +++ b/xml/System.Security/SecureString.xml @@ -62,7 +62,117 @@ Represents text that should be kept confidential, such as by deleting it from computer memory when no longer needed. This class cannot be inherited. - For more information about this API, see Supplemental API remarks for SecureString. + + [!IMPORTANT] +> We recommend that you don't use the `SecureString` class for new development on .NET (Core) or when you migrate existing code to .NET (Core). For more information, see [SecureString shouldn't be used](https://github.com/dotnet/platform-compat/blob/master/docs/DE0001.md). + +[!INCLUDE [context](includes/context.md)] + + is a string type that provides a measure of security. It tries to avoid storing potentially sensitive strings in process memory as plain text. (For limitations, however, see the [How secure is SecureString?](#how-secure-is-securestring) section.) The value of an instance of is automatically protected using a mechanism supported by the underlying platform when the instance is initialized or when the value is modified. Your application can render the instance immutable and prevent further modification by invoking the method. + +The maximum length of a instance is 65,536 characters. + +> [!IMPORTANT] +> This type implements the interface. When you have finished using an instance of the type, you should dispose of it either directly or indirectly. To dispose of the type directly, call its method in a `try`/`catch` block. To dispose of it indirectly, use a language construct such as `using` (in C#) or `Using` (in Visual Basic). For more information, see the "Using an Object that Implements IDisposable" section in the interface topic. + +The class and its members are not visible to COM. For more information, see . + +## String versus SecureString + +An instance of the class is both immutable and, when no longer needed, cannot be programmatically scheduled for garbage collection; that is, the instance is read-only after it is created, and it is not possible to predict when the instance will be deleted from computer memory. Because instances are immutable, operations that appear to modify an existing instance actually create a copy of it to manipulate. Consequently, if a object contains sensitive information such as a password, credit card number, or personal data, there is a risk the information could be revealed after it is used because your application cannot delete the data from computer memory. + +A object is similar to a object in that it has a text value. However, the value of a object is pinned in memory, may use a protection mechanism, such as encryption, provided by the underlying operating system, can be modified until your application marks it as read-only, and can be deleted from computer memory either by your application calling the method or by the .NET garbage collector. + +For a discussion of the limitations of the class, see the [How secure is SecureString?](#how-secure-is-securestring) section. + +## SecureString operations + +The class includes members that allow you to do the following: + +Instantiate a object +You instantiate a object by calling its parameterless constructor. + +Add characters to a object +You can add a single character at a time to a object by calling its or method. + +> [!IMPORTANT] +> A object should never be constructed from a , because the sensitive data is already subject to the memory persistence consequences of the immutable class. The best way to construct a object is from a character-at-a-time unmanaged source, such as the method. + +Remove characters from a object +You can replace an individual character by calling the method, remove an individual character by calling the method, or remove all characters from the instance by calling the method. + +Make the object read-only +Once you have defined the string that the object represents, you call its method to make the string read-only. + +Get information about the object +The class has only two members that provide information about the string: its property, which indicates the number of UTF16-encoded code units in the string; and the , method, which indicates whether the instance is read-only. + +Release the memory allocated to the instance +Because implements the interface, you release its memory by calling the method. + +The class has no members that inspect, compare, or convert the value of a . The absence of such members helps protect the value of the instance from accidental or malicious exposure. Use appropriate members of the class, such as the method, to manipulate the value of a object. + +The .NET Class Library commonly uses instances in the following ways: + +- To provide password information to a process by using the structure or by calling an overload of the method that has a parameter of type . + +- To provide network password information by calling a class constructor that has a parameter of type or by using the property. + +- To provide password information for SQL Server Authentication by calling the constructor or retrieving the value of the property. + +- To pass a string to unmanaged code. For more information, see the [SecureString and interop](#securestring-and-interop) section. + +## SecureString and interop + +Because the operating system does not directly support , you must convert the value of the object to the required string type before passing the string to a native method. The class has five methods that do this: + +- , which converts the string value to a binary string (BSTR) recognized by COM. + +- and , which copy the string value to an ANSI string in unmanaged memory. + +- and , which copy the string value to a Unicode string in unmanaged memory. + +Each of these methods creates a clear-text string in unmanaged memory. It is the responsibility of the developer to zero out and free that memory as soon as it is no longer needed. Each of the string conversion and memory allocation methods has a corresponding method to zero out and free the allocated memory: + +|Allocation and conversion method|Zero and free method| +|--------------------------------------|--------------------------| +||| +||| +||| +||| +||| + +## How secure is SecureString? + +When created properly, a instance provides more data protection than a . When creating a string from a character-at-a-time source, creates multiple intermediate in memory, whereas creates just a single instance. Garbage collection of objects is non-deterministic. In addition, because its memory is not pinned, the garbage collector will make additional copies of values when moving and compacting memory. In contrast, the memory allocated to a object is pinned, and that memory can be freed by calling the method. + +Although data stored in a instance is more secure than data stored in a instance, there are significant limitations on how secure a instance is. These include: + +Platform + +On the Windows operating system, the contents of a instance's internal character array are encrypted. However, whether because of missing APIs or key management issues, encryption is not available on all platforms. Because of this platform dependency, does not encrypt the internal storage on non-Windows platform. Other techniques are used on those platforms to provide additional protection. + +Duration + +Even if the implementation is able to take advantage of encryption, the plain text assigned to the instance may be exposed at various times: + +- Because Windows doesn't offer a secure string implementation at the operating system level, .NET still has to convert the secure string value to its plain text representation in order to use it. + +- Whenever the value of the secure string is modified by methods such as or , it must be decrypted (that is, converted back to plain text), modified, and then encrypted again. + +- If the secure string is used in an interop call, it must be converted to an ANSI string, a Unicode string, or a binary string (BSTR). For more information, see the [SecureString and interop](#securestring-and-interop) section. + +The time interval for which the instance's value is exposed is merely shortened in comparison to the class. + +Storage versus usage +More generally, the class defines a storage mechanism for string values that should be protected or kept confidential. However, outside of .NET itself, no usage mechanism supports . This means that the secure string must be converted to a usable form (typically a clear text form) that can be recognized by its target, and that decryption and conversion must occur in user space. + +Overall, is more secure than because it limits the exposure of sensitive string data. However, those strings may still be exposed to any process or operation that has access to raw memory, such as a malicious process running on the host computer, a process dump, or a user-viewable swap file. Instead of using to protect passwords, the recommended alternative is to use an opaque handle to credentials that are stored outside of the process. + + ]]> + to secure a user's password for use as a credential to start a new process. From 79bcfefcb38082d7c4ee87b6ee5491f4f086ab7e Mon Sep 17 00:00:00 2001 From: Genevieve Warren <24882762+gewarren@users.noreply.github.com> Date: Thu, 4 Jun 2026 14:56:33 -0700 Subject: [PATCH 2/2] remove unintentional file --- .../cpp/System/String/.ctor/sbyte_ctor1.cpp | 20 ------------------- 1 file changed, 20 deletions(-) delete mode 100644 snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp diff --git a/snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp b/snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp deleted file mode 100644 index f178c345ffc..00000000000 --- a/snippets/cpp/System/String/.ctor/sbyte_ctor1.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// SByte_Ctor1.cpp : Defines the entry point for the console application. -// - -//#include "stdafx.h" - -// -using namespace System; - -void main() -{ - char chars[] = { 'a', 'b', 'c', 'd', '\x00' }; - - char* charPtr = chars; - String^ value = gcnew String(charPtr); - - Console::WriteLine(value); -} -// The example displays the following output: -// abcd -//