11.Folosirea numarului variabil de argumente.

 - La crearea metodei de obicei se cunoaste numarul argumentelor, care vor fi transmise, dar nu intotdeauna. Uneori apare necesitatea de crea o metoda, careia sai putem transmite un numar arbitrar de argumente. Sa presupunem ca cream o metoda, care determina cea mai mica valoare dintr-un sir de valori. Unei astfel de metode i se poate de transmis nu mai putin de doua argumente. Dar in orice caz ea trebuie sa returneze cea mai mica valoare. Asa metoda nu se poate crea folosind parametrii obisnuiti.Suntem nevoiti sa folosim un tip de parametri speciali, care determina un numar arbitrar de argumente. Acest lucru se face cu parametrul de tip params. pentru a declara un masiv de parametri, capabil sa accepte citiva parametri, se va folosi modificatorul params. Numarulde elemete ale masivului va fi egal cu numaraul argumentelor, care se transmit metodei. Iar pentru primirea argumentelor in programa se organizeaza accesul la acest masiv.

Mai jos este un exemplu de prgrama,in care modificatorul params se foloseste pentru crearea metodei MinVal():


//folosire modificator params

using System;

class Min {
    public int MinVal(params int[] nums) {
        int m;

        if (nums.Length == 0) {
            Console.WriteLine("Eroare: nu sunt argumente. ");
            return 0;
        }

        m = nums[0];
        for (int i = 0; i < nums.Length; i++)
            if (nums[i] < m) m = nums[i];

        return m;
    }
}

namespace ParamsDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            Min ob = new Min();
            int min;
            int a = 10, b = 20;

            //apelare metoda cu doua argumente
            min = ob.MinVal(a, b);
            Console.WriteLine("Valoarea mai mica este: " + min);

            //apelare metoda cu trei argumente
            min = ob.MinVal(a, b, -1);
            Console.WriteLine("Valoarea mai mica este: " + min);

            //apelare metoda cu cinci argumente
            min = ob.MinVal(18, 23, 3, 14, 25);
            Console.WriteLine("Valoarea mai mica este: " + min);

            //apelare metoda cu un masiv de valori intregi
            int[] arguments = { 45, 67, 34, 9, 112, 8};
            min = ob.MinVal(arguments);
            Console.WriteLine("Valoarea mai mica este: " + min);

            Console.ReadKey(true);

        }
    }
}

Rezultat
Valoarea mai mica este: 10
Valoarea mai mica este: -1
Valoarea mai mica este: 3
Valoarea mai mica este: 8

 

De fiecare data, cind este apelata metoda MinVal(), i se transmite argumente in masivul nums. Lungimea acestui masiv este egal cu numarul de argumente transmise. De acea cu ajutorul metodei MinVal() se poate de determinat cea mai mica valoare dintre orice numar de valori.

In ultimul apel al metodei main, se trasnmite un masiv, care contine un sir de valori.Cind se creaza un parametru de tip params, acesta primeste lista de argumente cu lungime diferita, sau un masiv care contine argumente.

Toate argumentele transmise cu params trebuie sa fie de acelasi tipul masivului indicat la acest parametru.

 - Metodele pot avea si parametri obisnuiti si de tip params. EX:

//folosire modificator params impreuna cu parametru obisnuit

using System;

class MyClass {
    public void ShowArgs(string msg, params int[] nums) {
        Console.Write(msg + ": ");

        foreach (int i in nums)
            Console.Write(i + " ");

        Console.WriteLine();
    }
}

namespace ParamsDemo2
{
    class Program
    {
        static void Main(string[] args)
        {
            MyClass ob = new MyClass();

            ob.ShowArgs("Un sir de numere inteegi", 1, 2, 3, 4, 5);

            ob.ShowArgs("Iar acesta sunt inca doua numere ",
                         17, 20);

            Console.ReadKey(true);

        }
    }
}

Un sir de numere inteegi: 1 2 3 4 5
Iar acesta sunt inca doua numere : 17 20
 

 


12.Returnarea obectelor din metode 

 - Metodele pot returna toate tipurile de date inclusiv si tipul clasei. In exemplu de mai jos este prezentata clasa Rect, care contine metoda Enlarge(), in care se construieste un dreptungi cu aceleasi laturi, ca si la obiectul apelat, dar cu un coieficient de scalare diferit.


//returnare obiect din metoda

using System;

class Rect {
    int width;
    int height;

    public Rect(int w, int h) {
        width = w;
        height = h;
    }

    public int Area() {
        return width * height;
    }

    public void Show() {
        Console.WriteLine(width + " " + height);
    }

    /*<etoda returneaza un dreptunghi cu laturile,
      proprtional marite cu coeficientul indicat */
    public Rect Enlarge(int factor) {
        return new Rect(width * factor, height * factor);
    }
}

namespace Retobj
{
    class Program
    {
        static void Main(string[] args)
        {
            Rect r1 = new Rect(4, 5);

            Console.WriteLine("Marimea dreptunghiului r1: ");
            r1.Show();

            Console.WriteLine();

            //creare dreptunghi de doua ori mai mare
            Rect r2 = r1.Enlarge(2);

            Console.Write("Marimea dreptunghiului r2: ");
            r2.Show();
            Console.WriteLine("Suprafata dreptunghiului r2: " + r2.Area() );

            Console.ReadKey();
        }
    }
}

Marimea dreptunghiului r1:
4 5

Marimea dreptunghiului r2: 8 10
Suprafata dreptunghiului r2: 80

 

Cind metoda returneaza un obect, acesta continua sa existe atita timp cit spre el este o referinta.

 - Un exemplu practic este fabrica clasei, care reprezinta o metoda, destinata pentru construirea de obiecte  ale aceleiasi clase. In multe cazuri nu se recomanda de oferit acces utilizatorului la constructorul clasei.In asa situatii pentru construirea obiectelor se folosesc fabricile de clase.

EX.

//fabrica clasei

using System;

class MyClass {
    int a, b; //membri privati

    //creare fabrica a clasei MyClass
    public MyClass Factory(int i, int j){
        MyClass t = new MyClass();

        t.a = i;
        t.b = j;

        return t; //returneaza obiect
     }

    public void Show() {
        Console.WriteLine("a si b: " + a + " " + b);
    }
}


namespace MakeObjects
{
    class Program
    {
        static void Main(string[] args)
        {
            MyClass ob = new MyClass();
            int i, j;

            //creare obiect, folosind fabrica de clase
            for (i = 0, j = 0; i < 10; i++, j--) {
                MyClass anotherOb = ob.Factory(i, j); // creare obiect
                anotherOb.Show();
            }
            Console.WriteLine();

                Console.ReadKey();
        }
    }
}

a si b: 0 0
a si b: 1 -1
a si b: 2 -2
a si b: 3 -3
a si b: 4 -4
a si b: 5 -5
a si b: 6 -6
a si b: 7 -7
a si b: 8 -8
a si b: 9 -9

 

In acest exemplu nu este declarat un constructor, si de asta este accesibil doar cel by default. Acest lucru inseamna ca valorile variabilelor a si b nu se pot declara cu ajutorul constructorului. Dar in fabrica clasei Factory() se poate de creat obiecte, in care se dau valori variabilelor a si b. Mai mult decit atit, variabilele a si b sunt private, si de aceia valorile lor se pota declara daor prin intermediul fabricii clasei.

In Main() se creaza un obiect al clasei MyClass, iar metoda fabrica se foloseste in ciclul for pentru a crea alte obiecte. La fiecare pas al iteratiei se creaza o variabila referinta la obiectul anotherOb, careia i se atribuie o referinta la obiect, format de fabrica clasei. La terminarea fiecarui pas al iteratiei variabila anotherOb ese din domeniul de actiune a ciclului, iar obiectul, la care face referinta, se utilizeaza.


13.Returnarea masivelor din metode  p234