Лабораторная работа 1 2 лабораторная работа 2 31 лабораторная работа 3 44 лабораторная работа 4 74
Скачать 1.76 Mb.
|
5.4 Передача аргументовВообще, существуют два способа, с помощью которых машинный язык может передавать аргумент подпрограмме. Первый способ – передача аргумента по значению. Этот метод копирует значение аргумента в формальный параметр подпрограммы. Поэтому любые изменения этого параметра подпрограммой не имеют никакого влияния на соответствующий аргумент вызова. Второй способ – передача аргумента по ссылке. В этом методе ссылка на параметр (а не его значение) передается параметру. Внутри подпрограммы она используется, чтобы обратиться к фактическому параметру, указанному в вызове. Это означает, что изменения параметра будут влиять на аргумент, использованный для вызова подпрограммы. Java использует оба метода, в зависимости от того, что передается во время вызова подпрограмме. Когда методу передается простой тип, он передается по значению. Таким образом, то, что происходит с параметром, который принимает аргумент, никак не влияет на сам аргумент (т.е. аргумент при этом не изменяется). Например, рассмотрим следующую программу: // Простые типы передаются по значению. class Test { void meth(int i, int j) { i *= 2; j /= 2; } } class CallByValue { public static void main(String args[]) { Test ob = new Test(); int a = 15, b = 20; System.out.println("a и b перед вызовом: " + a + " " + b); ob.meth(a, b); System.out.println("a и b после вызова: " + a + " " + b) ; } } Вывод этой программы: a и b перед вызовом: 15 20 a и b после вызова: 15 20 Как видите, операции, которые происходят внутри meth(), никак не влияют на значения a и b, используемые в вызове (их значения здесь не изменялись до 30 и 10, хотя метод meth() и выполнил соответствующие вычисления над своими параметрами). Когда вы передаете методу объект, ситуация драматически изменяется, потому что объекты передаются по ссылке. Имейте в виду, что при создании переменной типа «класс», вы создаете только ссылку на объект. Таким образом, когда вы передаете эту ссылку методу, принимающий ее параметр будет ссылаться на тот же самый объект, что и аргумент. Это и означает, что объекты передаются методам по ссылке. Все изменения объекта внутри метода затрагивают объект, используемый как аргумент. Например, рассмотрим следующую программу: // Объекты передаются по ссыпке. class Test { int a, b; Test(int i, int j) { a = i; b = j; } // передать объект void meth(Test o) { o.a *= 2; o.b /= 2; } } class CallByRef { public static void main(String args[]) { Test ob = new Test(15, 20); System.out.println("ob.a и ob.b перед вызовом: " + ob.a + " " + ob.b); ob.meth(ob); System.out.println("ob.a и ob.b после вызова: " + ob.a + " " + ob.b); } } Эта программа генерирует следующий вывод: ob.a и ob.b перед вызовом: 15 20 ob.a и ob.b после вызова: 30 10 В этом случае действия внутри meth() воздействовали на объект, используемый как аргумент. При передаче объектной ссылки методу сама ссылка передается по значению. Однако, т.к. передаваемое значение ссылается на объект, копия этого значения будет ссылаться на тот же объект, что и соответствующий аргумент. Замечание. Простые типы передаются методу по значению, а объекты – по ссылке. 5.5 Возврат объектовМетод может возвращать любой тип данных, включая типы классов, которые вы создаете. Например, в следующей программе метод incrByTenO возвращает объект, в котором значение а на десять больше, чем в вызывающем объекте. // Возврат объекта. class Test { int a; Test(int i) { a = i; } Test incrByTen() { Test temp = new Test(a+10); return temp; } } class RetOb { public static void main(String args[]) { Test ob1 = new Test(2); Test ob2; ob2 = ob1.incrByTen() ; System.out.println("ob1.a: " + ob1.a); System.out.println("ob2.a: " + ob2.a); ob2 = ob2.incrByTen(); System.out.println("ob2.a после повторного увеличения: " + ob2.a); } } Вывод, сгенерированный этой программой: ob1.a: 2 ob2.a: 12 ob2.a после повторного увеличения: 22 Каждый раз, когда incrByTen() вызывается, создается новый объект, и ссылка на него возвращается вызывающей подпрограмме. Из предыдущей программы можно сделать следующий важный вывод: т.к. все объекты распределяются динамически с помощью операции new, вас не должен беспокоить выход объекта из области его видимости, потому что метод, в котором он был создан, завершается. Объект продолжает существовать, пока где-то в вашей программе присутствует ссылка на него. Когда же ссылок нет, то в следующем сеансе сборки «мусора» объект будет утилизирован. |