Полиморфизм - это способность программиста писать методы с тем же именем, которые делают разные вещи для разных типов объектов, в зависимости от потребностей этих объектов. Например, если вы разрабатывали класс под названием Fraction
и класс с именем ComplexNumber
, оба они могут включать в себя метод с именем display()
, но каждый из них будет реализовывать этот метод по-разному. Например, в PHP вы можете реализовать его следующим образом:
// Class definitions
class Fraction
{
public $numerator;
public $denominator;
public function __construct($n, $d)
{
// In real life, you'd do some type checking, making sure $d != 0, etc.
$this->numerator = $n;
$this->denominator = $d;
}
public function display()
{
echo $this->numerator . '/' . $this->denominator;
}
}
class ComplexNumber
{
public $real;
public $imaginary;
public function __construct($a, $b)
{
$this->real = $a;
$this->imaginary = $b;
}
public function display()
{
echo $this->real . '+' . $this->imaginary . 'i';
}
}
// Main program
$fraction = new Fraction(1, 2);
$complex = new ComplexNumber(1, 2);
echo 'This is a fraction: '
$fraction->display();
echo "\n";
echo 'This is a complex number: '
$complex->display();
echo "\n";
Выходы:
This is a fraction: 1/2
This is a complex number: 1 + 2i
Некоторые из других ответов, по-видимому, подразумевают, что полиморфизм используется только совместно с наследованием; например, возможно, Fraction
и ComplexNumber
реализуют абстрактный класс, называемый Number
, который имеет метод display()
, который обеим обязательным образом реализуют Fraction и ComplexNumber. Но вы не нуждаетесь в наследовании , чтобы воспользоваться полиморфизмом.
По крайней мере, на динамически типизированных языках, таких как PHP (я не знаю о C ++ или Java), полиморфизм позволяет разработчик вызывать метод, не зная тип объекта раньше времени, и полагая, что будет вызвана правильная реализация метода. Например, пользователь выбирает тип созданного Number
:
$userNumberChoice = $_GET['userNumberChoice'];
switch ($userNumberChoice) {
case 'fraction':
$userNumber = new Fraction(1, 2);
break;
case 'complex':
$userNumber = new ComplexNumber(1, 2);
break;
}
echo "The user's number is: ";
$userNumber->display();
echo "\n";
. В этом случае будет вызван соответствующий метод display()
, хотя разработчик не может заранее знать будет ли пользователь выбирать фракцию или комплексное число.
Когда вы объединяете массив со строкой в
vaTest(s1 + " 1 ");
Тогда ссылка на массив преобразуется в строку
[Ljava.lang.String;@2a139a55
Таким образом, метод vaTest получит [115 ]
[Ljava.lang.String;@2a139a55 1
в виде массива размером 1.
Он работает следующим образом:
s1
неявно преобразуется в строку (s1.toString()
), в результате получается [Ljava.lang.String;@2a139a55
. 1
добавляется к указанной выше строке. Это приводит к [Ljava.lang.String;@2a139a55 1
varargs()
. Когда вы делаете vaTest(s1 + " 1 ");
, строковое представление s1 будет использоваться из-за правил конкатенации строк (знак «+»). Поэтому вместо отформатированного массива вы получите что-то вроде: [Ljava.lang.String;@2a139a55
Замените его на vaTest(Arrays.toString(s1) + " 1 ");
, чтобы получить ожидаемый результат.