Updated: 06 December 2024
The Avalonia API https://reference.avaloniaui.net/api/
Freelance software engineer United Kingdom
Updated: 06 December 2024
The Avalonia API https://reference.avaloniaui.net/api/
Updated: 03 April 2024
Find all animals names starting with an uppercase C
.
string pattern = @"\b[C]\w+";
Regex rg = new Regex(pattern);
string animals = "Cat, dog, Camel, caribou";
MatchCollection matchedAnimals = rg.Matches(animals);
for (int count = 0; count < matchedAnimals.Count; count++)
Console.WriteLine(matchedAnimals[count].Value);
Updated: 07 July 2023
Custom date and time format strings
string ds = "Sat 23 Dec 2023";
DateTime dt = DateTime.ParseExact(ds, "ddd dd MMM yyyy", CultureInfo.InvariantCulture);
Console.Write(dt.ToString());
Specify year, month, day, hour, min, seconds, UTC timezone
DateTime dt = new DateTime(2015, 12, 31, 5, 10, 20, DateTimeKind.Utc);
Updated: 07 July 2023
A brief example
string pattern = @"\b(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\b";
Regex rg = new Regex(pattern);
string dates = "Tuesday 25th May & Monday 1st of Apr.";
MatchCollection matched_dates = rg.Matches(dates);
for (int count = 0; count < matched_dates.Count; count++)
Console.WriteLine(matched_dates[count].Value);
# May
# Apr
Updated: 22 June 2023
Updated: 30 January 2023
Properties enable a class to expose a public way of getting and setting values. Properties are special methods called accessors. A property is a member which can read, write or compute a private field.
The basic pattern involves a private backing field. Both get
and set
accessors may perform some conversion or computation on the data before it’s stored or returned.
public class TimePeriod
{
private double _seconds;
public double Hours
{
get { return _seconds / 3600; }
set
{
if (value < 0 || value > 24)
throw new ArgumentOutOfRangeException(nameof(value),
"The valid range is between 0 and 24.");
_seconds = value * 3600;
}
}
}
Useage
TimePeriod t = new TimePeriod();
// The property assignment causes the 'set' accessor to be called.
t.Hours = 24;
// Retrieving the property causes the 'get' accessor to be called.
Console.WriteLine($"Time in hours: {t.Hours}");
More succinctly with expression bodies
public class SaleItem
{
string _name;
decimal _cost;
public SaleItem(string name, decimal cost)
{
_name = name;
_cost = cost;
}
public string Name
{
get => _name;
set => _name = value;
}
public decimal Price
{
get => _cost;
set => _cost = value;
}
}
In some cases, property get
and set
accessors just assign/retrieve a value from a backing field without extra logic. By using auto-implemented properties, the C# compiler transparently provides the backing fields.
public class SaleItem
{
public string Name
{ get; set; }
public decimal Price
{ get; set; }
}
https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/properties
Updated: 28 January 2023
Generics are classes, structures, interfaces, and methods that have placeholders (type parameters) for one or more of the types that they store or use.
Generics introduces the concept of type parameters to .NET, which make it possible to design classes and methods that defer the specification of one or more types until the class or method is declared and instantiated by client code.
https://learn.microsoft.com/en-us/dotnet/csharp/fundamentals/types/generics
// Declare the generic class.
public class GenericList<T>
{
public void Add(T input) { }
}
Updated: 28 January 2023
Anonymous types provide a convenient way to encapsulate a set of read-only properties into a single object without having to explicitly define a type first.
var v = new { Amount = 108, Message = "Hello" };
Updated: 28 January 2023
A lambda expression is used to create an anonymous function. The lambda declaration operator =>
separates the lambda’s parameter list from its body.
Expression lambda. Returns the result of the expression
// (input-parameters) => expression
Statement lambda
// (input-parameters) => { <statement block> }
Action<string> greet = name =>
{
string greeting = $"Hello {name}";
Console.WriteLine(greeting);
};
// greet("World");
Input parameters
// none
Action line = () => Console.WriteLine();
// one
Func cube = x => x * x * x;
Func cube = (x) => x * x * x;
// two or more
Func testForEquality = (x, y) => x == y;
// with types
Func isTooLong = (int x, string s) => s.Length > x;
Discards specify input parameters which are not used in the expression
Func<int, int, int> constant = (_, _) => 42;
Updated: 09 August 2024
Establish a development environment inside a running container
docker run -it \
--volume $(pwd):/source \
--workdir /source \
mcr.microsoft.com/dotnet/sdk:6.0
docker run -it \
--volume $(pwd):/source \
--workdir /source \
mcr.microsoft.com/dotnet/sdk:7.0
docker run -it \
--volume $(pwd):/source \
--workdir /source \
mcr.microsoft.com/dotnet/sdk:8.0
Create a hello world project
dotnet new console --framework net7.0 --use-program-main --name myapp
Run the app
cd myapp
dotnet run
https://github.com/dotnet/dotnet-docker/blob/main/samples/dotnetapp/Dockerfile
Dockerfile
FROM mcr.microsoft.com/dotnet/sdk:6.0 AS build
WORKDIR /source
# copy csproj and restore as distinct layers
COPY *.csproj .
RUN dotnet restore
# copy and publish app and libraries
COPY . .
RUN dotnet publish -c Release -o /app --self-contained false --no-restore
# final stage/image
FROM mcr.microsoft.com/dotnet/runtime:6.0
WORKDIR /app
COPY --from=build /app .
ENTRYPOINT ["dotnet", "source.dll"]
Build image based on Dockerfile above, in the same directory
docker build -t dndev .
Run a container
docker run dndev