static void Main() { var section = InterfaceFunctions.ChooseSection <StructuresSections>(); switch (section) { case StructuresSections.ICollection: case StructuresSections.IList: case StructuresSections.ISet: case StructuresSections.IDictionary: { ICollectionTest.MethodsOfICollection(section); } break; case StructuresSections.ITest: { IList <string> testList = new MyList <string>(); testList.Add("Luka"); testList.Add("Jernej"); testList.Add("Borut"); Console.WriteLine($"Imamo {testList.Count} elementov!"); } break; case StructuresSections.TestSpeed: { TestSpeed.TestDataStructures(InterfaceFunctions.ChooseSection <TestAction>()); } break; case StructuresSections.HanoiExample: { Console.WriteLine("Hanoi example "); HanoiType type = Hanoi.SelectHanoiType(); Console.Write("Enter number of discs: "); int k = int.Parse(Console.ReadLine()); Console.WriteLine($"Running case: {type} with {k} discs:"); int numPegs = 4; // Delali bomo samo s štirimi stolpi Stopwatch sw = Stopwatch.StartNew(); Hanoi hanBasic = new Hanoi(k, numPegs, type); int length = hanBasic.ShortestPathForSmallDimension(out _); Console.WriteLine(); Console.WriteLine($"\n\nDimension: {k}; Steps: {length}; Time: {sw.Elapsed.TotalSeconds}"); Console.WriteLine(); } break; } Console.WriteLine(); Console.WriteLine("Končano"); Console.ReadLine(); }
public static void BasicLINQSyntax() { switch (InterfaceFunctions.ChooseSection <BasicsSubsection>()) { case BasicsSubsection.Basic: { // LINQ sintaksa je zelo podobna sintaksi SQL, // vendar ima malo spremenjen vrstni red // Select je vedno na koncu (lahko izberemo posamezne lastnosti) var queryGeneral = from animal in LINQDataSet.animals select animal; Console.WriteLine("\nSplošna poizvedba o vseh elementih"); queryGeneral.ReadEnumerable(); } break; case BasicsSubsection.Select: { // Izberemo lahko le nekatere lastnosti // in jih postavimo v nov (anonimen) objekt var queryGeneral2 = from animal in LINQDataSet.animals select new { animal.Species, animal.HasTail }; // Pripravimo anonimen objekt. Več v Arh, Q19. Console.WriteLine("\nSplošna poizvedba z izbranimi lastnostmi"); // Izpis anonimnega objekta zraven pripiše tudi imena lastnosti! queryGeneral2.ReadEnumerable(); } break; case BasicsSubsection.Sort: { // Elemente lahko uredimo - uporabimo spremenljivko animal var queryOrdered = from animal in LINQDataSet.animals orderby animal.NumberOfLegs descending select animal; Console.WriteLine("\nSplošna urejena poizvedba"); queryOrdered.ReadEnumerable(); } break; case BasicsSubsection.Filter: { // Ali filtriramo - spet uporabimo spremenljivko animal var queryFiltered = from animal in LINQDataSet.animals where animal.HasTail && animal.NumberOfLegs <= 4 // Filtriranje orderby animal.Species select animal;; Console.WriteLine("\nSplošna filtrirana poizvedba"); queryFiltered.ReadEnumerable(); } break; } // Več o sintaksi z uporabo "join" in "group by" v Arh, Q51 in Arh, Q54. }
/// <summary> /// Ker v metodi uporabljamo rezervirano besedo 'await', moramo /// metodi dodati določilo async. /// </summary> public static async void AsyncTest() { // Spet bomo uporabljali razred Task iz knjižnice System.Threading.Tasks // Task predstavlja operacijo, ki teče v ozadju (asinhrono ali v drugi niti) // Ponovimo primer iz drugega razdelka tega poglavja: Stopwatch sw = Stopwatch.StartNew(); var backgroundTask = Task.Run(() => CountPrimes(InterfaceFunctions.ChooseSection <ExecutionType>())); // PRIMER 1: Ko dostopimo do rezultata, bo trenutna nit počakala na rezultat (enako kot pri metodi Wait). Console.WriteLine($"Task smo zagnali, zdaj čakamo na rezultat."); var result = backgroundTask.Result; Console.WriteLine($"Čakamo, da task konča izračun."); Console.WriteLine($"In čakamo..."); Console.WriteLine($"In čakamo..."); Console.WriteLine($"Našli smo {result} praštevil v {sw.Elapsed.TotalSeconds} sekundah."); // PRIMER 2: Namesto čakanja lahko uporabimo rezervirano besedo await, // vendar nam v funkciji to ne spremeni obnašanja. // Se pa bo sprostila trenutna nit za ostale aktivnosti /* * Console.WriteLine($"Task smo zagnali, zdaj čakamo na rezultat."); * var result = await backgroundTask; * Console.WriteLine($"Čakamo, da task konča izračun."); * Console.WriteLine($"In čakamo..."); * Console.WriteLine($"In čakamo..."); * Console.WriteLine($"Našli smo {result} praštevil v {sw.Elapsed.TotalSeconds} sekundah."); * Console.WriteLine($"Do tukaj pridemo šele, ko imamo rezultat"); */ // PRIMER 3: Implementirajmo našo logiko v ločeni metodi // Klic deluje podobno kot pri await - le da se izvajanje nadaljuje samo znotraj metode /* * Console.WriteLine($"Task smo zagnali, zdaj čakamo na rezultat."); * var result = ResultAsync(); * Console.WriteLine($"Čakamo, da task konča izračun."); * Console.WriteLine($"In čakamo..."); * Console.WriteLine($"In čakamo..."); * Console.WriteLine($"Našli smo {result.Result} praštevil v {sw.Elapsed.TotalSeconds} sekundah."); * Console.WriteLine($"Do tukaj pridemo šele, ko imamo rezultat"); */ // Za konec velja pripomniti, da lahko z enim taskom opravimo več zaporednih opravil, // kar nam omogoča metoda ContinueWith. Ko se eno opravilo konča, lahko začnemo z naslednjim. }
static void Main(string[] args) { switch (InterfaceFunctions.ChooseSection <SerializationSections>()) { case SerializationSections.Serialize: SerializationBasics.Serialize(); break; case SerializationSections.Deserialize: SerializationBasics.Deserialize(); break; case SerializationSections.Cyclic: CyclicDependencies.CyclicSerialization(); break; } Console.ReadLine(); }
static void Main() { switch (InterfaceFunctions.ChooseSection <LINQSections>()) { case LINQSections.Basics: { Basics.BasicLINQSyntax(); } break; case LINQSections.MethodSyntax: { Methods.MethodLINQSyntax(); } break; case LINQSections.LambdaExpressions: { LambdaExpressions.LambdaTests(); } break; } Console.ReadLine(); }
static async Task Main(string[] args) { switch (InterfaceFunctions.ChooseSection <ConcurrentSection>()) { case ConcurrentSection.Multithreaded: { Multithreads.Multithreaded(); } break; case ConcurrentSection.Tasks: { Multithreads.Tasks(); } break; case ConcurrentSection.TasksWithResult: { Multithreads.TasksResult(); } break; case ConcurrentSection.Timers: { Timers.TimersTest(); } break; case ConcurrentSection.PLINQ: { ParallelLINQ.PLINQExample(); } break; case ConcurrentSection.PLINQOrdered: { ParallelLINQ.PLINQExampleOrdered(); } break; case ConcurrentSection.Async: { Asynchronous.AsyncTest(); // Ker await ne blokira izvajalne niti, pred izračunom pridemo iz funkcije Console.WriteLine("Smo na koncu primera!"); // Vrstni red čakanja na input ni popolnoma jasen... //Thread.Sleep(3000); Console.ReadLine(); } break; case ConcurrentSection.AsyncSeveral: { string keyword = "in"; Asynchronous.AsyncTestSeveral(keyword); Console.WriteLine($"Program se vmes nadaljuje..."); } break; case ConcurrentSection.AsyncFiles: { AsyncFiles.AsyncFilesTest(); } break; case ConcurrentSection.AsyncFilesCancel: { AsyncFiles.AsyncFilesTestWithCancel(); } break; case ConcurrentSection.AsyncFilesProgress: { AsyncFiles.AsyncFilesTestWithCancelAndProgress(); } break; case ConcurrentSection.Lock: { LockAndMonitor.LockExample(); } break; case ConcurrentSection.ComputePI: { ComputePI.ComputePITests(); } break; case ConcurrentSection.BreakfastBad: { PrepareBreakfastAsync.BreakfastBadExample(); } break; case ConcurrentSection.BreakfastGood: { //PrepareBreakfastAsync.BreakfastBadExample(); await PrepareBreakfastAsync.BreakfastGoodExample(); } break; } Console.ReadLine(); }
static void Main() { switch (InterfaceFunctions.ChooseSection <DesignPatternsSections>()) { case DesignPatternsSections.Singleton: { // Osnoven primer kreiranja singletona SingletonTests.CreateSingleton(); } break; case DesignPatternsSections.SingletonLog: { // Primer uporabe singletona za kreiranje objekta log (dnevnik dogodkov) SingletonTests.CreateLog(); } break; case DesignPatternsSections.FactoryBad: { // Slab primer izbire tipa kartice: // Tip kartice se izbere v GUI-ju CreditCardType type = InterfaceFunctions.ChooseSection <CreditCardType>(); // Pripravimo si novo spremenljivko ICreditCard card = null; // Ustvarimo instanco glede na izbrani tip switch (type) { case CreditCardType.Silver: card = new Silver(); break; case CreditCardType.Gold: card = new Gold(); break; case CreditCardType.Platinum: card = new Platinum(); break; } // Izpišemo podatke Console.WriteLine("Podatki o kartici:"); Console.WriteLine($" Tip: {card.CreditCardType}"); Console.WriteLine($" Limit: {card.Limit}"); Console.WriteLine($" Letni strošek: {card.AnnualCharge}"); /* * Težava pri zgornjem načinu je, da so uporabniški vmesnik in razredi kreditnih kartic * močno povezani. Če dodamo nov tip kartice, moramo to popraviti tudi v uporabniškem vmesniku, * saj je treba dopolniti switch. */ } break; case DesignPatternsSections.FactoryGood: { // V uporabniškem vmesniku ohranimo samo logiko, ki se tiče uporabnika CreditCardType type = InterfaceFunctions.ChooseSection <CreditCardType>(); ICreditCard card = CreditCardFactory.GetCreditCard(type); // Izpišemo podatke Console.WriteLine("Podatki o kartici:"); Console.WriteLine($" Tip: {card.CreditCardType}"); Console.WriteLine($" Limit: {card.Limit}"); Console.WriteLine($" Letni strošek: {card.AnnualCharge}"); } break; } Console.ReadLine(); }
static void Main() { switch (InterfaceFunctions.ChooseSection <ObjectsSections>()) { case ObjectsSections.Properties: { Properties.CheckProperties(); } break; case ObjectsSections.Indexers: { Indexers.TestIndexers(); } break; case ObjectsSections.BoxingUnboxing: { BoxingUnboxing.TestBoxing(); } break; case ObjectsSections.Inheritance: { // V namespace-u Inheritance smo naredili nov razdelek, // zato do ustrezne funkcije pridemo šele preko // ustrezne poti Inheritance.Inheritance.TestInheritance1(); } break; case ObjectsSections.InheritanceWithCasting: { Inheritance.Inheritance.TestInheritanceWithCasting(); } break; case ObjectsSections.InheritanceWithCastingOnOverriden: { Inheritance.Inheritance.TestInheritanceWithOverridenMethod(); } break; case ObjectsSections.InheritancePolymorphism: { Inheritance.Inheritance.TestInheritanceWithPolymorphisms(); } break; case ObjectsSections.Interfaces: { Interfaces.Interfaces.TestInterfaces(); } break; case ObjectsSections.Abstraction: { Abstraction.Abstraction.TestAbstraction(); } break; case ObjectsSections.InterfacesImplicitExplicit: { InterfacesImplicitExplicit.ImplicitExplicit.TestImplicitExplicit(); } break; case ObjectsSections.Extensions: { Extensions.Extensions.TestExtensions(); } break; } Console.ReadLine(); }
/// <summary> /// Arh, Q50 /// Za vse ukaze, ki smo si jih ogledali v metodi BasicLINQSyntax, /// imamo na voljo tudi razširitvene metode, /// ki nam omogočijo klice metod za posamezno akcijo /// </summary> public static void MethodLINQSyntax() { // LINQ sintaksa, ki smo jo predstavili zgoraj, // se prevede v klice funkcij. Te lahko uporabimo tudi mi. switch (InterfaceFunctions.ChooseSection <MethodsSubsection>()) { case MethodsSubsection.Basic: { /*var queryGeneral = from animal in LINQDataSet.animals * select animal; */ // Zgornjo kodo tako prepišemo v var queryGeneral = LINQDataSet.animals .Select(animal => animal); // Metoda Select 'projicira' vsak element zbirke v podano obliko Console.WriteLine("\nSplošna poizvedba o vseh elementih"); queryGeneral.ReadEnumerable(); } break; case MethodsSubsection.Select: { /*var queryGeneral2 = from animal in LINQDataSet.animals * select new { animal.Species, animal.HasTail };*/ var queryGeneral2 = LINQDataSet.animals .Select(animal => new { Species = animal.Species, Tail = animal.HasTail }); Console.WriteLine("\nSplošna poizvedba z izbranimi lastnostmi"); // Izpis anonimnega objekta zraven pripiše tudi imena lastnosti! queryGeneral2.ReadEnumerable(); } break; case MethodsSubsection.Sort: { /*var queryOrdered = from animal in LINQDataSet.animals * orderby animal.Species * select animal;*/ var queryOrdered = LINQDataSet.animals .OrderByDescending(animal => animal.NumberOfLegs) .ThenBy(animal => animal.Species) .Select(animal => animal); Console.WriteLine("\nSplošna urejena poizvedba"); queryOrdered.ReadEnumerable(); } break; case MethodsSubsection.Filter: { /*var queryFiltered = from animal in LINQDataSet.animals * orderby animal.Species * where animal.HasTail * select animal;*/ var queryFiltered = LINQDataSet.animals .OrderBy(animal => animal.Species) // Uredimo. Imamo tudi OrderByDescending // Za ureditev znotraj ureditve uporabimo ThenBy ali ThenByDescending .Where(animal => animal.HasTail) // Filtriramo .Select(animal => animal); // Povemo, katere lastnosti želimo v rezultatu Console.WriteLine("\nSplošna filtrirana poizvedba"); queryFiltered.ReadEnumerable(); } break; case MethodsSubsection.CallOrder: { // V standardni LINQ sintaksi je vrstni red ukazov pomemben // oziroma moramo select zapisati na koncu. // Pri razširitvenih metodah nam tega ni treba, // vendar moramo vedeti, da se klici v teh primerih izvedejo // v danem vrstnem redu. var querySelectFirst = LINQDataSet.animals .Select(animal => animal.Species) //.OrderBy(animal => animal.Species) // se ne prevede, ker smo izbrali le Species .OrderBy(species => species); //.Where(animal => animal.HasTail); // se ne prevede, ker smo izbrali le Species Console.WriteLine("\nPoizvedba samo z vrsto živali"); querySelectFirst.ReadEnumerable(); } break; case MethodsSubsection.SkipAndTake: { // Poleg osnovnih metod, ki omogočajo klice // funkcij iz standardne sintakse, pa imamo na voljo še nekaj // metod, ki poenostavijo delo s poizvedbami. var queryAdditional = LINQDataSet.animals .OrderBy(animal => animal.Species) .Where(animal => animal.HasTail) .Select(animal => animal) .Skip(1) // Preskoči prvih k (v našem primeru 1) zapisov .Take(1); // Vzemi k (v našem primeru 1) zapisov // Metodi Take in Skip sta lahko uporabni npr. pri implementaciji listanja po zapisih (paginaciji) } break; case MethodsSubsection.Any: { // Metoda Any preveri, če v zbirki obstaja vsaj en element za dani pogoj var existsWithTail = LINQDataSet.animals.Any(x => x.HasTail); Console.WriteLine($"\n{(existsWithTail ? "Obstaja vsaj ena žival z repom!" : "Ne obstaja žival z repom!")}"); } break; case MethodsSubsection.All: { // Metoda All preveri, če vsi elementi v zbirki ustrezajo danemu pogoju var allWithTail = LINQDataSet.animals.All(x => x.HasTail); Console.WriteLine($"\n{(allWithTail ? "Vse živali imajo rep!" : "Nimajo vse živali repa!")}"); } break; case MethodsSubsection.SelectMany: { // Metodo SelectMany uporabimo, ko imajo objekti osnovnega predikata za lastnost sezname, // mi pa želimo narediti poizvedbo po teh seznamih (s tem se izognemo dvojnim zankam). // Pri tem nas ne zanima, iz seznama katerega objekta smo zapise dobili. var selectingMany = LINQDataSet.continents .SelectMany(continent => continent.Animals) .Where(animalID => LINQDataSet.animals.Find(x => x.ID == animalID)?.NumberOfLegs == 4) .Select(animalID => LINQDataSet.animals.Find(x => x.ID == animalID).Species); Console.WriteLine($"\nŽivali na vseh celinah, ki imajo štiri noge, so: "); selectingMany.ReadEnumerable(); } break; case MethodsSubsection.Distinct: { // Paziti moramo na to, da se izbor ne naredi po različnih vnosih (dobili smo več enakih ID-jev) // Da poskrbimo za to, uporabimo metodo Distinct. Tej metodi lahko kot parameter podamo tudi // objekt tipa IEqualityComparer, ki določi, kateri pari instanc naj bodo obravnavani kot enaki (več v Arh, Q52). var selectingManyDistinct = LINQDataSet.continents .SelectMany(continent => continent.Animals) .Distinct() .Where(animalID => LINQDataSet.animals.Find(x => x.ID == animalID)?.NumberOfLegs == 4) .Select(animalID => LINQDataSet.animals.Find(x => x.ID == animalID).Species) .OrderBy(x => x); Console.WriteLine($"\nRazlične živali na vseh celinah so: "); selectingManyDistinct.ReadEnumerable(); } break; case MethodsSubsection.Aggregate: { // Podobno kot metodi All in Any, lahko uporabimo metodi Count in CountLong // za vračanje števila instanc, ki ustrezajo pogoju podanemu kot argument obeh metod. // Brez argumenta metodi vrneta število vseh instanc v naboru. // Na voljo imamo tudi metode Min, Max, Average ter Sum, ki vračajo to, kar povejo njihova imena. // Bolj zanimiva je metoda Aggregate. // Poiščimo žival, ki ima najmanj nog var queryAggMinLegsAnimal = LINQDataSet.animals .Aggregate <Animal, Animal, string>( // Tip elementa seznama, tip iskane vrednosti, tip rezultata seed: null, // Določitev začetne vrednosti iskane instance // Prehod po vseh instancah z upoštevanjem pogoja (minLegs, animal) => (minLegs == null || minLegs.NumberOfLegs > animal.NumberOfLegs) ? animal : minLegs, minLegs => minLegs?.Species // Rezultat, ki ni nujno instanca, ampak le kakšna izmed lastnosti ); Console.WriteLine($"\nNajmanj nog ima {queryAggMinLegsAnimal}!"); var queryAggMinLegsNumber = LINQDataSet.animals .Aggregate <Animal, int, int>( // Tip elementa seznama, tip iskane vrednosti, tip rezultata seed: int.MaxValue, // Določitev začetne vrednosti iskane instance // Prehod po vseh instancah z upoštevanjem pogoja (minLegs, animal) => (minLegs == int.MaxValue || minLegs > animal.NumberOfLegs) ? animal.NumberOfLegs : minLegs, minLegs => minLegs // Rezultat ); Console.WriteLine($"\nNajmanjše število nog je {queryAggMinLegsNumber}!"); } break; } }
public static void LambdaTests() { // V LINQ imamo dve vrsti razširitvenih metod // - metode za vmesnik IEnumerable<T>, ko po podatkih poizvedujemo lokalno // - metode za vmesnik IQueryable<T>, ko poizvedujemo po podatkih na zunanjem viru // Preden si ogledamo razlike med njima, definirajmo lambda-izraz. // Lambda izrazi so oblike // (vhodni parametri) => ukaz ali // (vhodni parameter) => {zaporedje ukazov} // Gre za skrajšan zapis funkcij. switch (InterfaceFunctions.ChooseSection <LambdaSubsections>()) { case LambdaSubsections.FunctionWithLambda: { // Celo definiramo jih lahko in kličemo na različnih mestih. Func <int, int, (int, int)> sum = (x, y) => (x + y, x - y); Func <double, int> roundUp = x => (int)Math.Round(x, 0, MidpointRounding.AwayFromZero); Func <double, int> roundDown = x => (int)Math.Round(x, 0); double x = Math.PI; Console.WriteLine($"Zaokrožimo število {x}: {roundUp(x)}"); Console.WriteLine($"Zaokrožimo število 4.5 navzgor: {roundUp(4.5)}"); Console.WriteLine($"Zaokrožimo število 4.5 navzdol: {roundDown(4.5)}"); Console.WriteLine($"Zaokrožimo število 4.5001 navzgor: {roundUp(4.5001)}"); Console.WriteLine($"Zaokrožimo število 4.5001 navzdol: {roundDown(4.5001)}"); } break; case LambdaSubsections.ThreeFunctionSyntaxes: { // LINQ poizvedbo torej lahko izvedemo na tri različne načine var queryLambda = LINQDataSet.animals.Where(x => x.NumberOfLegs < 4); Console.WriteLine($"\nObičajni lambda izraz:"); queryLambda.ReadEnumerable(); var queryDelegate = LINQDataSet.animals .Where(delegate(Animal x) { return(x.NumberOfLegs < 4); }); Console.WriteLine($"\nAnonimna metoda:"); queryDelegate.ReadEnumerable(); var queryFunction = LINQDataSet.animals.Where(LessThan4Long); Console.WriteLine($"\nPosebej definirana funkcija:"); queryFunction.ReadEnumerable(); // Razlika med zgornjimi tremi klici je zgolj v sintaksi, // pri izvedbi pa se bodo obnašale enako, če smo na IEnumerable<T> instanci, // saj je parameter teh metod oblike Func<,> (npr. Func<T,bool>). // POZOR! // Pri metodah vmesnika IQueryable moramo kot parameter podati objekte // tipa Expression<Func<,>> (npr. Expression<Func<T,bool>>). // Razlika v kodi ne bo opazna, vsi trije načini se prevedejo, // vendar se le za lambda izraz filtriranje izvede na podatkovni strukturi, // kjer delamo poizvedbo. // Za druga dva načina se podatki najprej prenesejo // k nam in filtrirajo na naši strani, // kar lahko prinese velike časovne razlike. // Na to moramo torej paziti, ko implementiramo svoje metode, // ki delajo poizvedbe na podatkovni bazi - vračanje IQueryable<T> ali IEnumerable<T> // lahko bistveno upočasni našo aplikacijo. } break; } }
private static async Task <int> ResultAsync() { var backgroundTask = Task.Run(() => CountPrimes(InterfaceFunctions.ChooseSection <ExecutionType>())); return(await backgroundTask); }
static void Main(string[] args) { // Poženemo primer glede na izbrano sekcijo // Namesto funkcije ChooseExampleSection uporabimo bolj splošno generično funkcijo ChooseSection, // ki smo jo pripravili v razredni knjižnici (class library) in izpiše možne vrednosti za // poljubno enumeracijo. switch (/*ChooseExampleSection()*/ InterfaceFunctions.ChooseSection <IntroductorySections>()) { case IntroductorySections.HelloWorld: { // V tem primeru si ogledamo preprosto metodo, ki naredi izpis v konzolo HelloWorld(); } break; case IntroductorySections.CountingPrimes: { // V tem primeru si ogledamo glavno sintakso C# (zanke, izbirne stavke) int numPrimes = MyStaticFunctions.CountPrimes(20); Console.WriteLine(numPrimes); } break; case IntroductorySections.PreparingOutputs: { // V tem primeru si ogledamo možnosti izpisa z uporabo interpolacije PrepareOutputs(); } break; case IntroductorySections.CountingPrimesWithOut: { // V tem primeru si ogledamo vračanje vrednosti z uporabo določila out int upToNumber = 90; int numPrimes = MyStaticFunctions.CountPrimes(upToNumber, out int largest); Console.WriteLine($"Od 1 do {upToNumber} je {numPrimes} praštevil, največje pa je {largest}."); } break; case IntroductorySections.CountingPrimesAndTuples: { // V tem primeru si ogledamo vračanje vrednosti s pomočja strukture Tuple // https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/builtin-types/value-tuples int upToNumber = 20; (int numPrimes, int largest) = MyStaticFunctions.CountPrimesAndFindLargest(upToNumber); Console.WriteLine($"Od 1 do {upToNumber} je {numPrimes} praštevil, največje pa je {largest}."); } break; case IntroductorySections.RandomLists: { // V tem primeru si ogledamo // - generiranje naključnih števil // - uporabo seznamov // - uporabo neobveznih parametrov // - uporabo lambda izrazov (k njim se vrnemo še kasneje) List <int> lstRnd = MyStaticFunctions.MakeRandomList(13, out int odds, true); Console.WriteLine($"\nŠtevilo vnosov je {lstRnd.Count}, od teh je lihih {odds}"); } break; case IntroductorySections.RandomListsWithoutOut: { // V tem primeru si ogledamo // - kako se izogniti definiranju out spremenljivke, če je ne uporabljamo List <int> lstRnd = MyStaticFunctions.MakeRandomList(13, out _); Console.WriteLine($"\nŠtevilo vnosov je {lstRnd.Count}"); } break; case IntroductorySections.WritingInFile: { // V tem primeru si ogledamo zapisovanje v datoteko MyStaticFunctions.WriteFile("PrvaPredavanjaTest3.txt"); } break; case IntroductorySections.ReadingFromFile: { // V tem primeru si ogledamo branje iz datoteke int numLines = MyStaticFunctions.ReadFile("PrvaPredavanjaTest2.txt"); Console.WriteLine($"\nDatoteka vsebuje {numLines} vrstic"); } break; case IntroductorySections.ReadingFromFileWithObject: { // V tem primeru si ogledamo branje iz datoteke in // - zapisovanje lastnosti v poseben objekt // - lastnosti in njihove posebnosti (k njim se vrnemo malo kasneje) FileData fileData = MyStaticFunctions.ReadFile2("PrvaPredavanjaTest.txt"); Console.WriteLine($"Datoteka vsebuje {fileData.NumberOfLines} vrstic in " + $"{(fileData.ContainsSensitiveInfo ? "vsebuje moje ime!" : "ne vsebuje mojega imena!")}"); } break; case IntroductorySections.RecallingObjects: { // V tem primeru si osvežimo spomin na definiranje novega tipa (objekta) CreateStudents(); } break; } Console.Read(); }