Hello, I'm Mateusz Roth. Versatile Software Engineer from 🇵🇱🇪🇺, specialized in JavaScript, TypeScript, Node.js, React. I'm eager to work with Node.js, Python, Golang, serverless or IoT. Open-minded, friendly person that loves learning.
class should have just a one purpose - so for example Animal class shouldn’t perform logs to different outputs or shouldn’t perform a role of database of animals
animal class shouldn’t be responsible for database management like saving
O - OCP - Open/Closed Principle
classes should be open for extensions (new methods) but closed for modifications (don’t change method) - I’d say, you can change methods but not the contract what they receive and return
I’d say this role is more about abstraction and use of inheritance, for example by having a base class Animal with method makeSound, which is going to be implemented by child classes Lion or Snake
You see, for every new animal, a new logic is added to the AnimalSound function. This is quite a simple example. When your application grows and becomes complex, you will see that the if statement would be repeated over and over again in the AnimalSound function each time a new animal is added, all over the application. Do instead:
if something uses a class, it should be able to use the class and the base class / child class of it
sub-class must be substitutable for its super-class
PL: nie sprawdzamy typu klasy, wykorzystujemy metody wirtualne i implementujemy je różnie w róznych klasach, ale wywołujemy tak samo
I - ISP - Interface Segregation Principle
you should write few interfaces instead of a big one interface that contains all the interfaces
make fine grained interfaces that are client specific
clients should not be forced to depend upon interfaces that they do not use
PL: nie tworzymy metod, których nie będziemy mogli zaimplementować w klasach korzystających z interfejsu, np. przykład z draw vs drawCircle, drawTriangle
D - DIP - Dependency Inversion Principle
you should create new class by placing in the constructor of it the interface of a class that the new class depends on
PL: polegamy na interfejsach, nie ich implementacjach - aby można było podmienić lub zamockować
typy wartościowe (value types) - w tym również struct
typy referencyjne (reference types)
typy wskaźnikowe (pointer types)
konwersja niejawna (implicit type conversion)
konwersja jawna (explicit type conversion)
zmienne, typy integralne (integral types)
typy zmiennoprzecinkowe (floating point types)
typy dziesiętne (decimal types)
typy logiczne (boolean types)
typy puste (nullable types)
Stałe i literały:
Stałe odnoszą się do wartości, których program nie może zmieniać w trakcie wykonywania. Te stałe wartości nazywane są również literałami. Stałe traktowane są jak zwykłe zmienne z zaznaczeniem, że ich wartości nie mogą być modyfikowane.
parametry typu wartościowego, referencyjnego, wyjściowego
typy puste
tablice wielowymiarowe
tablice postrzępione
klasa Array
Klasy:
Klasa może dziedziczyć z jednej klasy, ale może implementować wiele interfejsów
metody klasy (methods)
pola klasy (fields)
właściwości klasy (properties) - Właściwości nie służą do przechowywania wartości. Przy pomocy accesorów mają dostęp do pól, które reprezentują.
Class member, np. pole lub metoda
Class members, in C#, are the members of a class that represent the data and behavior of a class.
Class members are members declared in the class and all those (excluding constructors and destructors) declared in all classes in its inheritance hierarchy.
Class members can be of the following types:
Constants representing constant values
Fields representing variables
Methods providing services like calculation or other actions on its members
Properties that define the class features and include actions to fetch and modify them
Events generated to communicate between different classes /objects
Indexers that help in accessing class instances similar to arrays
Operators that define semantics when used in expressions with class instances
Instance constructors to initialize members of class instances
Static constructor to initialize the class itself
Destructors to execute actions necessary to be performed before class instances are discarded
Types that are local to the class (nested type)
Class members are initialized in constructors which can be overloaded with different signatures. For classes that do not have constructor, a default constructor that initializes the class members (to default values) will be generated.
struktury struct - W języku C# struktura to wartościowy typ danych.
Klasy i struktury mają następujące różnice:
klasy są typem referencyjnym a struktury typem wartościowym;
struktury nie wspierają dziedziczenia;
struktury nie mogą mieć domyślnego konstruktora.
Dalej o klasach:
konstruktor i destruktor klasy
statyczne składniki klasy
Składniki statyczne możemy zdefiniować za pomocą słowa kluczowego static. Jeżeli zadeklarujemy składową jako statyczną nie ważne jak wiele obiektów klasy utworzymy, istnieje zawsze tylko jedna kopia składowej statycznej.
klasa statyczna
Możemy utworzyć statyczną klasę. Klasa taka mówi, iż nie została napisana po to, aby tworzyć nowe obiekty. Nawet, gdybyśmy chcieli utworzyć nowy obiekt klasy statycznej kompilator zgłosi błąd. Mogą być wywołane bez tworzenia instancji danej klasy.
dziedziczenie - inheritance
klasa bazowa i pochodna - base/parent and derived/child class
polimorfizm - polymorphism
statyczny polimorfizm, tj. przeciążanie metod i przeciążanie operatorów
polimorfizm dynamiczny, czyli klasy abstrakcyjne i metody wirtualne
Polimorfizm dynamiczny jest realizowany za pomocą klas abstrakcyjnych oraz metod wirtualnych. Metoda może mieć różne implementacje dla różnych klas.
Klasa abstrakcyjna. Klasa taka zawiera abstrakcyjne metody, których implementacja zależy od wykorzystania w poszczególnych klasach pochodnych.
Poniżej lista zasad, o których należy pamiętać, tworząc klasy abstrakcyjne:
nie można utworzyć instancji klasy abstrakcyjnej;
nie można zadeklarować metody abstrakcyjnej poza klasą abstrakcyjną;
kiedy klasa opatrzona jest modyfikatorem dostępu sealed nie może być dziedziczona. Dodatkowo, klasa abstrakcyjna nie może być zdefiniowana jako sealed.
metody wirtualne
Jeżeli masz zdefiniowaną metodę w klasie bazowej, ale chcesz, żeby została zaimplementowana w klasach pochodnych możesz do tego celu zastosować metody wirtualne.
interfejsy
Język C# nie obsługuje wielokrotnego dziedziczenia. Klasa może dziedziczyć po jednej klasie bazowej, ale może implementować wiele interfejsów.
Typy generyczne pozwalają na opóźnienie w dostarczeniu specyfikacji typu danych w elementach takich jak klasy czy metody do momentu użycia ich w trakcie wykonywania programu. Innymi słowy, typy generyczne pozwalają na napisanie klasy lub metody, która może działać z każdym typem danych.
Kod niezabezpieczony lub też kod niekontrolowany to blok kodu używający wskaźników.
Część 3
Inne materiały i informacje
Implicit Interface Implementation vs Explicit Interface Implementation
Implicit: you access the interface methods and properties as if they were part of the class.
1 2 3 4 5 6 7 8 9 10 11
publicclassTest : ITest { publicstring Id // Generated by Implement Interface { get { thrownew NotImplementedException(); } } }
Test t = new Test(); t.Id; // OK ((ITest)t).Id; // OK
Explicit: you can only access methods and properties when treating the class as the implemented interface.
1 2 3 4 5 6 7 8 9 10 11 12 13 14
publicclassTest : ITest { string ITest.Id // Generated by Implement Interface Explicitly { get { thrownew NotImplementedException(); } } }
Test t = new Test(); t.Id; // Not OK ((ITest)t).Id; // OK
ITest it = t; it.Id; // OK
It allows you to implement two interfaces that define the same method. However, if you explicitly implement the interface, the methods can only be accessed when the variable is typed to that explicit interface.
The fact that a struct can implement an interface is well known and so is the fact that casting a value type into an interface leads to boxing of the value type. This is because methods in interfaces are defined as virtual and to resolve virtual references, vtable (method table) look up is required. Since value types do not have pointers to vtable they are first boxed into a reference type and then the look up happens. https://blogs.msdn.microsoft.com/abhinaba/2005/10/05/c-structs-and-interface/
Po polsku, chodzi o to, że kiedy jako struct zaimplementujemy jakiś interface , to struct będzie zapakowany w dodatkowy obiekt. Metody wywoływane na instancji tego struct, który jest rzutowany na interface , na przykład:
1 2 3 4 5 6 7 8
Employee employee = new Employee("Cool Guy", 65); IPromotion p = employee; Console.WriteLine(employee); p.promote(); Console.WriteLine(employee);
//Cool Guy (65) //Cool Guy (65)
modyfikują wartości tego dodatkowego obiektu, a nie w oryginalnym obiekcie employee. Jeśli zmienimy struct na class to nie będzie tego boxowania, tworzenia dodatkowego obiektu i wszystko będzie działać jak należy. Wynika to z tego, że:
casting a value type into an interface leads to boxing of the value type
This is because methods in interfaces are defined as virtual and to resolve virtual references, vtable (method table) look up is required. Since value types do not have pointers to vtable they are first boxed into a reference type and then the look up happens.
First login to NPM using npm adduser or npm login command source. Now go to a new project folder and run npm init and create an index.js file with exports object. Then run npm publish, now you can install your package in another project. You can also use npm link to link your package globally.
Release a new version of a npm package
Simply use command npm version <update_type> where <update_type> is one of the semantic versioning release types, patch, minor, or major source.