markdown _notes.md
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了markdown _notes.md相关的知识,希望对你有一定的参考价值。
## C# workflows
### Simple Console Application
1. open visual studio
2. File > New > Project > Installed > Visual C# > .NET Core > Console App (.NET Core)
3. Specify Name and Location
4. Create new solution (default)
5. Create directory for solution (default)
6. click 'OK'
## C# Resources
### docs
[C# language ref](https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/)
[C# programming guide](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/index)
[C# in Visual Studio](https://docs.microsoft.com/en-us/visualstudio/ide/tutorial-csharp-aspnet-core)
### sites
* [2,000 Things You Should Know About C#](https://csharp.2000things.com/)
### courses
[C# beginers training course](https://mva.microsoft.com/en-US/training-courses/c-fundamentals-for-absolute-beginners-16169?l=Lvld4EQIC_2706218949)
[Programming in C# Jump Start](https://mva.microsoft.com/en-US/training-courses/programming-in-c-jump-start-14254?l=j0iuozSfB_6900115888)
[Up and Running with C#]()
[C#: Delegates, Events and Lambdas (lynda)](https://www.lynda.com/C-tutorials/C-Delegates-Events-Lambdas/370499-2.html)
[C#: Interfaces and Generics (lynda)](https://www.lynda.com/C-tutorials/C-Interfaces-Generics/388134-2.html)
### reference texts
C# in a nutshell
C# cookbook
effective C#
## notes on C#
### C# language features & gotchas
* C# objects have 1 of 3 types: value, reference, pointer.
* All value types derive from **System.ValueType**, and *all* types derive from **System.Object**.
* Value types are stored on the stack (well [sort of](http://www.yoda.arachsys.com/csharp/memory.html)), passed by value (copied), and include built-in and immutable structures (i.e., structs and enums). Reference types are stored on the heap, are passed by ref, and include interfaces and mutable structures (i.e., classes)
* managed language (depends on .NET CLR virtual machine)
* "var" can be used to *infer* a strong type (not same as a dynamic variable that can *change* type, but as shorthand, AND also *must* be used when [storing an anonymous type object](https://stackoverflow.com/a/4307487/1525466), e.g., `var foo = new { Bar = "bar"};`)
* support **Anonymous Types**, Structs and **Value Tuples** for creating simple property groupings when creating full-blown class is overkill (though anonymouse types are actually implemented as classes behind scenes) and only need to use in local scope (not portable).
* supports SQL-esq declarative query expressions, called LINQ queries (can function like python list compressions)
* support **extension methods**, syntactic sugar for adding *static* functionality to an existing type, without having to create a derived type (and without breaking encapsulation similar to the way decorators wrap a function).
* Can turn off compile-time type checking with **Dynamics** (e.g. to simplify interaction with external objects), i.e., *defers* type checking to run-time (so can still handle type errors with run-time exceptions ala-python).
* supports namespace aliasing with `using` (this is *NOT* an import statement. To import in C# you "add a reference" to the build)
* supports simple *enum* implementation `cards = enum {HEARTS, SPADES, CLUBS}`
* supports type safe function objects, called delegates, that can be passed around at runtime (similar to C++ function pointers or callbacks).
* support event listening/handling, which implements something like pub/sub pattern?
see also:
https://www.quora.com/Can-C-do-everything-that-Python-can
### classes
* Use static class to group static methods (no properties, i.e. stateless)
* Use abstract class to define base behaivior of related classes. Abstract methods have no imlpementation; they *must* be implemented by all derived classes.
* Declare class **sealed** to prevent inheritence or extension (except through extension methods, b/c they do not break encapsulation.)
* Break a class into multiple parts, across mult. files, with **partial**. Or use add additional behaivor to a partial class without creating a derived class (esp, when partial is created externally, e.g. by a framework)
* 4 levels of accisibility: Public, Private (scoped to enclosing namespace or class), Internal (scoped to project or "assembly"), Protected (only this class and derived classes can access)
* In C#, "properties" define get/set methods for private "variables" and have implicit notation with no "()", get *never* accepts args and set *always* accepts one arg which is implicitly passed with keyword "value".
* Also a shorthand notion for properties `public int x { get; set; }` if no need to verify that user is providing valid input to set.
* only **single inheritence** allowed (interfaces provide similar role as multiple inheritence)
* Derived class can override **virtual** base class method only.
* acheives **polymorphism** thru casting (to base types or interface types it implements).
* Base class can also declare methods **virtual** to ensure overriden implementations gets used even in the case of instance being cast to its base class type polymorphically. Derrived methods that are declared **new** (explicitely or implicitely by default) on the other hand, will permit casting to base class.
### Structs (i.e., Named Tuples) and Value Tuples (i.e., Tuples):
* supports **structs**, a value type that is basically a simple immutable class for grouping related variables (i.e., namedtuples).
* Prefer structs over *very* small classes (structs are faster b/c take advantage of high-speed sequential access) with *very* few instances (becauses class cost of high overhead can't be paid for if not sharing class definition in memory), esp if *not* passing around, *BUT* [You can pass a struct by reference using thcaseharp.2000things.com/2011/03/20/276-passing-a-struct-by-reference/))
* as of 7.0, support **Value Tuples** for grouping related values (i.e., tuples)
* Prefer tuple over struct for concise syntax (including support for single line unpacking)
* If just want to return multiple values, Out parameters are [fast and cheap](https://stackoverflow.com/a/6381959/1525466) (but require that you pass in a variable, and rely upon mutation).
---
C# programming guide
https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide
### [Arrays](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/arrays/)
* Arrays are an enumerable (i.e., use lazy evaluation, and can be iterated over with a *foreach* loop) reference type (i.e, is passed by reference)
* You can create an empty array `int[] a = new int[5]` or a full array `int[] b = {1,2,3};`, or even an implicitly typed array `var c = new[] {1,2,3}`. If empty, numeric elements are set to zero, and reference elements are set to null (e.g., jagged arrays are arrays of arrays)
* C# [Arrays are objects](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/arrays/arrays-as-objects) (like python and Java, unlike C and C++), with useful methods/properties for sorting, searching, and copying, etc...
* An array can be Single-Dimensional, Multidimensional or Jagged. Use `GetLength(i)` to get length of dimension i in multidimensional arrays.
* [Pass array with `out` or `ref`](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/arrays/passing-arrays-using-ref-and-out) to initialize or completely change the reference object that the passed array variable points to. Note, any other variables which referred to the original array would *still* refer to the original array (kind of a hack to change size of an array, i.e., treat it like a dynamic array).
### [classes and structs](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/)
* Classes are reference types, use to model more complex behavior, or data that is intended to be modified after a class object is created.
* Structs are value types, they are best suited for small data structures that contain data that is not intended to be modified after the struct is created.
...
### classes and structs / Local Functions
* C# doesn't support functions that are declared outside of classes, so all functions are methods, with arguable exception of [local functions](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/local-functions) and [lambda expression](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/statements-expressions-operators/lambda-expressions).
* [local functions](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/local-functions) are implicitly private/non-static, and do not permit access modifiers.
* All local variables that are defined in the containing member, including its method parameters, are accessible in the local function.
* Local functions limit access to a function from a single class member (in this way they are **more than private**).
* Local functions are [very similar to lambda expressions](https://docs.microsoft.com/en-us/dotnet/csharp/local-functions-vs-lambdas), but [more efficient for the case when you want to write a function that is called only from the context of another method.](https://docs.microsoft.com/en-us/dotnet/csharp/local-functions-vs-lambdas)
### [Object and Collection initializers](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/object-and-collection-initializers)
* Use [Object initializer Syntax](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/object-and-collection-initializers) to create an instance of an object *javascript-style*, e.g., `Cat cat = {Name = "Fluffy"}`, without having to invoke a constructor, e.g., `Cat cat = new Cat("Fuffy")`
* Use Object initializer Syntax with `var` and `new` to create an [anonymous type](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/anonymous-types) that derive directly from object, e.g., `var v = new { Amount = 108, Message = "Hello" };`
### [Structs](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/structs)
```csharp
public struct CoOrds
{
public int x, y; // cannot initialize
// no default constructor allowed
public CoOrds(int p1, int p2)
{
x = p1;
y = p2;
}
}
...
// This works (like a class)
CoOrds a = new CoOrds(2,3);
// This also works!
CoOrds b;
b.x = 2;
b.y = 3;
// careful, this makes a full copy!
CoOrds c = b;
```
* Structs share most of the same syntax as classes, but are more limited.
* fields cannot be initialized unless they are declared as const or static
* struct cannot declare a default constructor (a constructor without parameters) or a finalizer. Constructors with params are allowed.
* Structs are **value types**, so When a struct is assigned to a new variable, all the data is copied!!!
* Unlike classes, structs can be [instantiated without using a new operator](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/using-structs#description-1).
* A struct cannot inherit from another struct or class, BUT they can implement interfaces [via boxing](https://blogs.msdn.microsoft.com/abhinaba/2005/10/05/c-structs-and-interface/).
* A struct can be used as a nullable type and can be assigned a null value???
### [Tuples](https://docs.microsoft.com/en-us/dotnet/csharp/tuples)
```csharp
// Unnamed Tuple with implicitly named fields: "Item1" and "Item2"
var unnamed = ("apple", 2);
// Named Tuple with explicitly named fields: "a" and "b"
var named = (a: "apple", b: 2);
// Tuple with named fields, "a" and "b", projected, ie, infered.
var a = "apple";
var b = 2;
var projected = (a, b);
// Reassign a tuple with compatible tuple (same size/field types)
named = unnamed;
// Return a tuple from a method like This
return named;
// Or return a tuple literal!
return ("apple", 2);
// Unpack with new explicitly/implicitly typed variables
(string item, int count) = ("apple", 2);
var (item, count) = ("apple", 2);
// Unpack with existing variables
string item;
int count;
(item, count) = ("apple", 2);
```
* `ValueTuples` replace existing generic/reference-typed Tuple classes, but prior 4.7, you must add the NuGet package `System.ValueTuple`. From here on, tuple refers to ValueTuple.
* Tuples are immutable, fixed-size groupings of heterogeneous objects.
* Tuples enable you to package multiple values in a single object easily.
* Prefer struct or class when defining a type with both data and behavior. Prefer tuple for just data.
* Unnamed tuples, have implicitly named fields named Item1, Item2, etc..
* Named Tuples have explicitly named fields with `name:value` notation.
* Names can infered, i.e., [projected](https://docs.microsoft.com/en-us/dotnet/csharp/tuples#tuple-projection-initializers), from variable names, if no explicit name is provided.
* Tuples can be a mix of implicitly, projected, and explicitly named field, where projected takes precedence over implicit, and explicit over projected.
* assignment allowed between tuple types that have same number of elements and type or [implicit conversions](https://docs.microsoft.com/en-us/dotnet/csharp/tuples#assignment-and-tuples) for the types via casting.
* Unpack, ie [Deconstruct](https://docs.microsoft.com/en-us/dotnet/csharp/tuples#deconstruction), a tuple with new or existing variables.
### [Delegates](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/delegates/)
* Delegates are *like* functions in functional languages or function pointers in C++ (except they are type safe and can be chained together). Because the instantiated delegate is an object, it can be passed around, or swapped out at run-time, i.e. used as a callback function.
* Unlike function objects in javascript or python, C# delegates are type safe, *so* they must be declared, and all delegate methods must have same signature.
* In some ways [delegates are also *like* interfaces](https://stackoverflow.com/a/8694947/1525466) (think strategy pattern) except you can specify [multiple delegate instances in a single class](https://stackoverflow.com/a/8694949/1525466). (see [When to Use Delegates Instead of Interfaces](https://msdn.microsoft.com/en-us/library/ms173173.aspx))
* Specifically, delegates [implement the strategy pattern](https://stackoverflow.com/a/529539/1525466) (can also implement strategy pattern with interfaces).
* Delegates can be [static functions, instance methods, or anonymous functions](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/delegates/how-to-declare-instantiate-and-use-a-delegate).
* [lambda expressions](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/statements-expressions-operators/lambda-expressions) are just shorthand anonymous delegates.
* Delegates are [*intentionally* not supported in Java](https://en.wikipedia.org/wiki/Comparison_of_C_Sharp_and_Java#Delegates,_method_references).
* A delegate can call more than one method when invoked. This is referred to as [multicasting](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/delegates/how-to-combine-delegates-multicast-delegates) and is used extensively in event handling.
* The +/- operators can be used to add/remove component delegates to/from a multicast delegate's invocation list to form **a chain of delegates**.
* Calling a multicast delegate calls the component delegates sequentially in the order that they were added to the "chain".
* Multicast delegate that accepts a `ref` parameter implement a pipeline, i.e., the reference is passed to each delegate in turn, and changes by one are visible to the next.
* Unhandled exceptions will break chain and pass exception to the caller (i.e., no subsequent delegates will be called.)
* Multicast delegates are [not intended to be used with delegates that return values](https://blog.slaks.net/2011/08/delegates-vs-function-pointers-addendum.html) b/c only the return value of the last method is returned.
* delegate types are derived from [System.Delegate](https://docs.microsoft.com/en-us/dotnet/api/system.delegate?view=netframework-4.7.2) and delegates with more than one method in their invocation list derive from [MulticastDelegate](https://docs.microsoft.com/en-us/dotnet/api/system.multicastdelegate?view=netframework-4.7.2).
### [Enumeration Types](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/enumeration-types)
### [Events](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/events/)
### [Exceptions and Exception Handling](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/exceptions/)
### [File System and the Registry](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/file-system/)
### [Generics](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/generics/)
* Create a Genertic class with **type parameters**, e.g., `public class GenericList<T> {...}`, for compile-time type-safty, memory efficiency, and performance (esp. when the list items are value types).
* Consider descriptive names for type parameters if there are more than one, e.g. `TInput, TOutput, TKey, TValue, TSession, etc.`
* Prefer [generic collections](https://docs.microsoft.com/en-us/dotnet/api/system.collections.generic) over Boxing/Unboxing, i.e type-casting to/from Object, whenever possible.
* Prefer [generic collections](https://docs.microsoft.com/en-us/dotnet/api/system.collections.generic) over ArrayList, i.e., implicit type-casting to/from Object, for *homogenous* collections.
* [Constrain genertic types](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/generics/constraints-on-type-parameters) with `where`, e.g., `public class GenericList<T> where T : BaseTypeClass`, to permit only certain types, e.g., only value or ref types, only those types that inherit from a particular base type, etc.
* Type parameters with no constraint are [unbounded](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/generics/constraints-on-type-parameters#unbounded-type-parameters)
* One or more parameter types may be constrained by one or more constraints. May even be constrained by other parameter types, e.g. `public class SampleClass<T, U, V> where T : V { }`
continue on https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/generics/generic-classes
### [Indexers](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/indexers/)
### [Interfaces](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/interfaces/)
* An interface [is like an abstract base class](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/interfaces/#interfaces-summary) but there is no base implementation and and class/struct that implements an interface must implement all its members.
* An interface defines a *behaivor* that a class (OR a struct!) can implement.
* C# does NOT support multiple class inheritance, but multiple interfaces are allowed.
* Structs cannot inherent from base class, but they can implement interfaces.
* Interfaces can **only include methods, properties, events, and indexers**. Members are implicitly public--no access modifiers are not allowed.
* members of the implementing class **must be public and non-static**, and have the same name and signature as the interface member.
* Generic typing is permitted in interface method signatures, eg. `interface IEquatable<T> { bool Equals(T obj); }`
* The interface itself provides no functionality that a class/struct can inherit. However, if a base class implements one or more interface(s), any class that is derived from that base class inherits all its implementation(s)!!! This is how limitation of no multiple inheritance is overcome!!!
* Interfaces can also implement other interfaces, and "derived" classes can reimplement the interfaces that is "inherits"
* Use [Explicit Implementation]() if a class implements two interfaces that contain a member with the same signature, then create and instance and cast that instance to another instance with `as` or `()` casting notation, before calling corresponding method on that instance.
```csharp
interface IEnglishDims{ float Length(); }
interface IMetricDims{ float Length(); }
class Box : IEnglishDims, IMetricDims
{
float lengthInches;
public Box(float length, float width) { lengthInches = length; }
// 1. Explicit Implementations of each interfaces
float IEnglishDims.Length() { return lengthInches; }
float IMetricDims.Length() { return lengthInches * 2.54f; }
static void Main()
{
// 2. Declare a class instance
Box box1 = new Box(30.0f, 20.0f);
// 3. Cast to desired interface
IEnglishDims eDims = (IEnglishDims)box1;
// 4. Get length in inches
System.Console.WriteLine(eDims.Length());
}
}
```
(adapted from [example](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/interfaces/how-to-explicitly-implement-members-of-two-interfaces#example))
### [Interoperability](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/interop/)
### [Main() and Command-Line Arguments](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/main-and-command-args/)
### [Namespaces](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/namespaces/)
### [Nullable Types](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/nullable-types/)
### [Programming Concepts](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/concepts/)
### [Statements, Expressions, and Operators](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/statements-expressions-operators/)
* The conditional operator `x?y:z` is the only ternary operator in C#.
* Conditionally access members with `x?.y`
* Create null default/fallback with `x??y`, called **null coalescing**.
* Support *arrow notation* for lambda expressions, e.g., `(T x) => y`
### [Strings](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/strings/)
### [Types](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/types/)
### [Unsafe Code and Pointers](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/unsafe-code-pointers/)
### [XML Documentation Comments](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/xmldoc/xml-documentation-comments)
以上是关于markdown _notes.md的主要内容,如果未能解决你的问题,请参考以下文章