Skip to content

Commit

Permalink
Merge pull request #8 from HamletTanyavong/dev
Browse files Browse the repository at this point in the history
Update documentation
  • Loading branch information
HamletTanyavong authored Sep 29, 2023
2 parents af41f0f + 6a3f8d0 commit 01d55c9
Show file tree
Hide file tree
Showing 13 changed files with 237 additions and 12 deletions.
2 changes: 2 additions & 0 deletions .github/FUNDING.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
github: HamletTanyavong
patreon: HamletTanyavong
5 changes: 3 additions & 2 deletions Mathematics.NET.sln
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution
.gitattributes = .gitattributes
.gitignore = .gitignore
LICENSE = LICENSE
README.md = README.md
EndProjectSection
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "tests", "tests", "{91DB0FE7-BAA4-4D16-8A39-65332DD53662}"
Expand All @@ -27,10 +28,10 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = ".github", ".github", "{9EB2
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "workflows", "workflows", "{1B32D7FF-257B-49BB-B495-D64E5E6C4C82}"
ProjectSection(SolutionItems) = preProject
.github\workflows\generate-gh-pages.yml = .github\workflows\generate-gh-pages.yml
.github\workflows\generate-documentation-site.yml = .github\workflows\generate-documentation-site.yml
EndProjectSection
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Mathematics.NET.DevApp", "src\Mathematics.NET.DevApp\Mathematics.NET.DevApp.csproj", "{89C3482F-0027-483E-AAD7-5E12453915B3}"
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Mathematics.NET.DevApp", "src\Mathematics.NET.DevApp\Mathematics.NET.DevApp.csproj", "{89C3482F-0027-483E-AAD7-5E12453915B3}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Expand Down
12 changes: 12 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<h1 align="center">Mathematics.NET</h1>

<p align="center">Mathematics.NET is a C# class library that provides tools for solving mathematical problems.</p>

[![GitHub](https://img.shields.io/github/license/HamletTanyavong/Mathematics.NET?style=flat-square&logo=github&labelColor=87cefa&color=ffd700)](https://github.com/HamletTanyavong/Mathematics.NET)
[![GitHub Repo Stars](https://img.shields.io/github/stars/HamletTanyavong/Mathematics.NET?color=87cefa&style=flat-square&logo=github)](https://github.com/HamletTanyavong/Mathematics.NET/stargazers)
[![NuGet](https://img.shields.io/nuget/v/Physics.NET.Mathematics?style=flat-square&logo=nuget)](https://www.nuget.org/packages/Physics.NET.Mathematics)
[![NuGet](https://img.shields.io/nuget/dt/Physics.NET.Mathematics?style=flat-square&logo=nuget)](https://www.nuget.org/packages/Physics.NET.Mathematics)

## Documentation

Please visit the [documentation site](https://mathematics.hamlettanyavong.com) for detailed information.
70 changes: 70 additions & 0 deletions docs/articles/fundamentals/numeric-types.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
# Numeric Types

There are three numeric types that can be used to represent complex, real, and rational numbers in Mathematics.NET.

All Mathematics.NET numbers implement the [IComplex<T, U>](https://mathematics.hamlettanyavong.com/api/Mathematics.NET.Core.IComplex-2.html) interface. Particularly useful is the fact that, unlike .NET runtime's [INumberBase\<T\>](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/INumberBase.cs), `IComplex<T, U>` defines the `Conjugate` method; this is incredibly helpful in avoiding code duplication for calculations involving complex and real numbers.

## Floating-Point Types

Floating-point Mathematics.NET numbers may be backed any number that implements [IFloatingPointIee754\<T\>](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/IFloatingPointIeee754.cs) and [IMinMaxValue\<T\>](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/IMinMaxValue.cs), or more specifically, [float](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Single.cs), [double](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Double.cs), and [decimal](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Decimal.cs).

### Complex Numbers

To create a complex number, we choose a backing type, in this case `double`, and write
```csharp
Complex<double> z = new(3, 4);
```
This represents the number $ z = 3+i4 $. We can also specify only one number to create a complex number with no imaginary part
```csharp
Complex<double> z = 3;
```
which represents $ z = 3 $.

### Real Numbers

Likewise, to create a real number, write
```csharp
Real<double> z = 1;
```
With real numbers, we can also get maximum and minimum values which will depend on the backing type.
```csharp
Console.WriteLine("Max value with float backing type: {0}", Real<float>.MaxValue);
Console.WriteLine("Max value with double backing type: {0}", Real<double>.MaxValue);
```
This will output `Max value with float backing type: 3.4028235E+38`
and `Max value with double backing type: 1.7976931348623157E+308`.

## Binary Types

Rational numbers are the only Mathematics.NET type in this category.

### Rational Numbers

Rational numbers require two backing types, one that implements [IBinaryInteger\<T\>](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/IBinaryInteger.cs) and one that implements both [IFloatingPointIee754\<T\>](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/IFloatingPointIeee754.cs) and [IMinMaxValue\<T\>](https://github.com/dotnet/runtime/blob/main/src/libraries/System.Private.CoreLib/src/System/Numerics/IMinMaxValue.cs).

With this information, we can create the following rational numbers:
```csharp
Rational<int, double> a = 2;
Rational<byte, float> b = new(2, 3);
Rational<BigInteger, double> c = new(3, 4);
```
which represent $ a = 2 $, $ b = 2/3 $, and $ c = 3/4 $.

The first type parameter indicates that the constructor only accepts values of that type. In these cases, `a` must be an int, `b` must be a byte, and `c` must be a BigInteger. The second parameter indicates the desired floating-point type with which we want to represent the rational number. We can get this value in two ways, e.g.
```csharp
Console.WriteLine(b.Value);
Console.WriteLine((float)b);
```
which will both output `0.6666667`.

> [!CAUTION]
> The floating-point representation of rational numbers may not be accurate in all cases.
We can also convert a floating-point number into a rational number with an explicit cast
```csharp
Console.WriteLine((Rational<int, double>)3.14);
```
> [!NOTE]
> The conversion conversion is not guaranteed to create the "best" fraction; for instance, the value $ 0.3333333333333333 $ will not produce $ 1/3 $ but instead produce $ 8333333333333331 / 25000000000000000 $.
Be aware that there are performance penalties with converting rationals to and from real numbers. An overflow exception will also be thrown if a value being converted cannot be represented by the target type.
Original file line number Diff line number Diff line change
@@ -1,14 +1,21 @@
# Installation

Mathematics.NET is available to download from [nuget](https://www.nuget.org).
Mathematics.NET is available to download from [nuget](https://www.nuget.org/packages/Physics.NET.Mathematics).

## Polyglot Notebooks
# [Package Reference](#tab/package-reference)

To use Mathematics.NET in you project, add the following line to your .csproj file:
```xml
<PackageReference Include="Physics.NET.Mathematics" Version="" />
```

# [Polyglot Notebooks](#tab/polyglot-notebooks)

Please have [Visual Studio Code](https://code.visualstudio.com/) installed as well as the [Polyglot Notebooks](https://marketplace.visualstudio.com/items?itemName=ms-dotnettools.dotnet-interactive-vscode) extension installed to begin using Mathematics.NET. When that is complete, create a new .ipynb file and add the following line to import the package:
```csharp
#r "nuget: Mathematics.NET"
#r "nuget: Physics.NET.Mathematics"
```
To get a specific version of Mathematics.NET, use, for example,
```csharp
#r "nuget: Mathematics.NET, 1.0.0"
#r "nuget: Physics.NET.Mathematics, 0.1.0-alpha.1"
```
6 changes: 5 additions & 1 deletion docs/articles/toc.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,8 @@
- name: Get Started
items:
- name: Installation
href: getstarted/installation.md
href: get_started/installation.md
- name: Fundamentals
items:
- name: Numeric Types
href: fundamentals/numeric-types.md
2 changes: 2 additions & 0 deletions docs/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,5 @@ Mathematics.NET is a C# class library that provides tools for solving mathematic

[![GitHub](https://img.shields.io/github/license/HamletTanyavong/Mathematics.NET?style=flat-square&logo=github&labelColor=87cefa&color=ffd700)](https://github.com/HamletTanyavong/Mathematics.NET)
[![GitHub Repo Stars](https://img.shields.io/github/stars/HamletTanyavong/Mathematics.NET?color=87cefa&style=flat-square&logo=github)](https://github.com/HamletTanyavong/Mathematics.NET/stargazers)
[![NuGet](https://img.shields.io/nuget/v/Physics.NET.Mathematics?style=flat-square&logo=nuget)](https://www.nuget.org/packages/Physics.NET.Mathematics)
[![NuGet](https://img.shields.io/nuget/dt/Physics.NET.Mathematics?style=flat-square&logo=nuget)](https://www.nuget.org/packages/Physics.NET.Mathematics)
38 changes: 38 additions & 0 deletions src/Mathematics.NET/Core/Extensions.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
// <copyright file="Extensions.cs" company="Mathematics.NET">
// Mathematics.NET
// https://github.com/HamletTanyavong/Mathematics.NET
//
// MIT License
//
// Copyright (c) 2023 Hamlet Tanyavong
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
// </copyright>

using System.Numerics;

namespace Mathematics.NET.Core;

public static class Extensions
{
public static Rational<T, U> Reduce<T, U>(this Rational<T, U> r)
where T : IBinaryInteger<T>
where U : IFloatingPointIeee754<U>, IMinMaxValue<U>
=> Rational<T, U>.Reduce(r);
}
12 changes: 8 additions & 4 deletions src/Mathematics.NET/Core/Rational.cs
Original file line number Diff line number Diff line change
Expand Up @@ -123,12 +123,17 @@ public Rational(T p, T q)
public static Rational<T, U> operator +(Rational<T, U> x, Rational<T, U> y)
{
var lcm = LCM(x._denominator, y._denominator);
return new(lcm / x._denominator * x._numerator + lcm / y._denominator * y._numerator, lcm);
var num = lcm / x._denominator * x._numerator + lcm / y._denominator * y._numerator;
var gcd = GCD(num, lcm);
return new(num / gcd, lcm / gcd);
}

public static Rational<T, U> operator -(Rational<T, U> x, Rational<T, U> y)
{
var lcm = LCM(x._denominator, y._denominator);
return new(lcm / x._denominator * x._numerator - lcm / y._denominator * y._numerator, lcm);
var num = lcm / x._denominator * x._numerator - lcm / y._denominator * y._numerator;
var gcd = GCD(num, lcm);
return new(num / gcd, lcm / gcd);
}

public static Rational<T, U> operator *(Rational<T, U> x, Rational<T, U> y)
Expand Down Expand Up @@ -269,7 +274,6 @@ public bool TryFormat(Span<char> destination, out int charsWritten, ReadOnlySpan
int charsCurrentlyWritten = 0;

bool tryFormatSucceeded;
int tryFormatCharsWritten;

if (_numerator == T.Zero)
{
Expand All @@ -292,7 +296,7 @@ public bool TryFormat(Span<char> destination, out int charsWritten, ReadOnlySpan
return false;
}

tryFormatSucceeded = _numerator.TryFormat(destination[charsCurrentlyWritten..], out tryFormatCharsWritten, null, provider);
tryFormatSucceeded = _numerator.TryFormat(destination[charsCurrentlyWritten..], out int tryFormatCharsWritten, null, provider);
charsCurrentlyWritten += tryFormatCharsWritten;
if (!tryFormatSucceeded || destination.Length < charsCurrentlyWritten + 1)
{
Expand Down
27 changes: 27 additions & 0 deletions src/Mathematics.NET/Mathematics.NET.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,35 @@
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<Platforms>x64</Platforms>
<Title>Mathematics.NET</Title>
<Version>0.1.0-alpha.1</Version>
<Authors>Hamlet Tanyavong</Authors>
<Description>Mathematics.NET is a C# class library that provides tools for solving mathematical problems.</Description>
<PackageTags>mathematics; math; maths</PackageTags>
<PackageLicenseFile>LICENSE</PackageLicenseFile>
<IncludeSymbols>True</IncludeSymbols>
<SymbolPackageFormat>snupkg</SymbolPackageFormat>
<PackageProjectUrl>https://mathematics.hamlettanyavong.com</PackageProjectUrl>
<Copyright>Copyright (c) 2023 Hamlet Tanyavong</Copyright>
<PackageReadmeFile>README.md</PackageReadmeFile>
<RepositoryUrl>https://github.com/HamletTanyavong/Mathematics.NET</RepositoryUrl>
<PackageReleaseNotes>This project is in alpha and is not yet ready for release.</PackageReleaseNotes>
<PackageRequireLicenseAcceptance>True</PackageRequireLicenseAcceptance>
<RunAnalyzersDuringBuild>True</RunAnalyzersDuringBuild>
<PackageId>Physics.NET.Mathematics</PackageId>
</PropertyGroup>

<ItemGroup>
<None Include="..\..\LICENSE">
<Pack>True</Pack>
<PackagePath>\</PackagePath>
</None>
<None Include="..\..\README.md">
<Pack>True</Pack>
<PackagePath>\</PackagePath>
</None>
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\Mathematics.NET.SourceGenerators\Mathematics.NET.SourceGenerators.csproj" OutputItemType="Analyzer" ReferenceOutputAssembly="false" />
</ItemGroup>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,11 +33,23 @@ public class ComplexDivisionBenchmarks
public Complex<double> Z { get; set; }
public Complex<double> W { get; set; }

public System.Numerics.Complex X { get; set; }
public System.Numerics.Complex Y { get; set; }

[GlobalSetup]
public void GlobalSetup()
{
Z = new(1.23, 2.34);
W = new(4.56, 3.45);

X = new(1.23, 2.34);
Y = new(4.56, 3.45);
}

[Benchmark(Baseline = true)]
public System.Numerics.Complex SystemDivision()
{
return X / Y;
}

[Benchmark]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ public Real<double> SystemComplexAbs()
}

[Benchmark]
public Real<double> ComplexAbs()
public Complex<double> ComplexAbs()
{
return Complex<double>.Abs(W);
}
Expand Down
46 changes: 46 additions & 0 deletions tests/Mathematics.NET.Tests/Core/RationalTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,52 @@ namespace Mathematics.NET.Tests.Core;
[TestCategory("Core"), TestCategory("Rational Number")]
public sealed class RationalTests
{
[TestMethod]
[DataRow(2, 4, 5, 3, 13, 6)]
public void Add_TwoRationalsOfIntAndDouble_ReturnsReducedSum(int inANum, int inADen, int inBNum, int inBDen, int expectedNum, int expectedDen)
{
Rational<int, double> x = new(inANum, inADen);
Rational<int, double> y = new(inBNum, inBDen);
Rational<int, double> expected = new(expectedNum, expectedDen);

var actual = x + y;

Assert.AreEqual(expected, actual);
}

[TestMethod]
public void Divide_RationalOfIntAndDoubleByZero_ReturnsNaN()
{
var actual = Rational<int, double>.One / Rational<int, double>.Zero;

Assert.AreEqual(Rational<int, double>.NaN, actual);
}

[TestMethod]
[DataRow(2, 3, 4, 8, 1, 3)]
public void Multiply_TwoRationalsOfIntAndDouble_ReturnsReducedProduct(int inANum, int inADen, int inBNum, int inBDen, int expectedNum, int expectedDen)
{
Rational<int, double> x = new(inANum, inADen);
Rational<int, double> y = new(inBNum, inBDen);
Rational<int, double> expected = new(expectedNum, expectedDen);

var actual = x * y;

Assert.AreEqual(expected, actual);
}

[TestMethod]
[DataRow(6, 8, 3, 4)]
public void Reduce_RationalOfIntAndDouble_ReturnsReducedFraction(int inNum, int inDen, int expectedNum, int expectedDen)
{
Rational<int, double> p = new(inNum, inDen);
Rational<int, double> expected = new(expectedNum, expectedDen);

var actual = p.Reduce();

Assert.AreEqual(expected, actual);
}

[TestMethod]
[DataRow(3, 4, 7)]
public void TryFormat_RationalOfIntAndDoubleWithAdequateDestinationLength_ReturnsTrue(int inNum, int inDen, int length)
Expand Down

0 comments on commit 01d55c9

Please sign in to comment.