Programing

약한 유형의 언어와 관련하여 명백한 모순에 대해 설명하기

crosscheck 2020. 5. 21. 20:34
반응형

약한 유형의 언어와 관련하여 명백한 모순에 대해 설명하기


필자는 강력한 타이핑을 이해한다고 생각 하지만 약한 타이핑에 대한 예제를 찾을 때마다 유형을 자동으로 강제 변환 / 변환하는 프로그래밍 언어의 예제를 찾습니다.

예를 들어, Typing : Strong vs. Weak 라는 기사 에서 Static vs. Dynamic 은 다음 과 같은 경우 예외가 발생하므로 Python이 강력하게 입력된다고 말합니다.

파이썬

1 + "1"
Traceback (most recent call last):
File "", line 1, in ? 
TypeError: unsupported operand type(s) for +: 'int' and 'str'

그러나 Java와 C #에서는 그러한 일이 가능하며 그 유형에 대해서만 약한 유형으로 간주하지는 않습니다.

자바

  int a = 10;
  String b = "b";
  String result = a + b;
  System.out.println(result);

씨#

int a = 10;
string b = "b";
string c = a + b;
Console.WriteLine(c);

Weakly Type Languages 라는 다른 기사 에서 저자는 Perl이 명시 적으로 변환되지 않고 문자열을 숫자로 또는 그 반대로 연결할 수 있기 때문에 약하게 유형이 지정되었다고 말합니다.

$a=10;
$b="a";
$c=$a.$b;
print $c; #10a

따라서 동일한 예제는 Perl을 약하게 입력했지만 Java 및 C #?는 아닙니다.

이봐, 혼란스러워 여기에 이미지 설명을 입력하십시오

저자는 다른 유형의 값에 대한 특정 작업의 적용을 방해하는 언어가 강력하게 입력되고 반대로 의미가 약한 유형임을 암시하는 것으로 보입니다.

따라서 언젠가는 언어가 많은 자동 변환을 제공하거나 유형 사이의 강제 변환이 (약식으로) 약한 유형으로 간주 될 수 있지만, 약간의 변환 만 제공하는 다른 언어는 결국에는 강력하게 입력 된 것으로 간주됩니다.

그러나 나는이 해석에있어서 틀렸다는 것을 믿어야하는데, 왜 그것을 어떻게 설명해야하는지 모른다.

그래서 내 질문은 :

  • 언어가 실제로 약하게 입력되었다는 것은 실제로 무엇을 의미합니까?
  • 언어에 의해 수행되는 자동 변환 / 자동 강제와 관련이없는 약한 타이핑의 좋은 예를 언급 할 수 있습니까?
  • 언어를 동시에 약하고 타이핑 할 수 있습니까?

업데이트 : 이 질문은 2012 년 10 월 15 일에 제 블로그의 주제였습니다. 훌륭한 질문에 감사드립니다!


언어가 "약하게 입력 된"다는 것은 무엇을 의미합니까?

"이 언어는 내가 싫어하는 타입 시스템을 사용합니다"라는 의미입니다. 대조적으로 "강력한 유형의"언어는 유쾌한 유형 시스템을 갖춘 언어입니다.

용어는 본질적으로 의미가 없으므로 피해야합니다. Wikipedia 에는 "강력한 유형"에 대한 11 가지 다른 의미가 나열되어 있으며 그 중 일부는 모순됩니다. 이는 "강력한 유형"또는 "약한 유형"이라는 용어가 포함 된 대화에서 혼동이 발생할 가능성이 높다는 것을 나타냅니다.

실제로 확실하게 말할 수있는 것은 논의중인 "강력한 유형의"언어가 런타임 또는 컴파일 타임에 유형 시스템에 추가 제한이 있다는 점입니다. 논의중인 "약한 유형의"언어는 부족합니다. 추가 제한 없이는 그러한 제한을 결정할 수 없습니다.

"강력한 유형"및 "약한 유형"을 사용하는 대신 어떤 종류의 유형 안전을 의미하는지 자세히 설명해야합니다. 예를 들어 C #은 대부분 정적으로 형식이 지정된 언어이며 형식이 안전한 언어이며 메모리가 안전한 언어 입니다.. C #을 사용하면 이러한 세 가지 "강력한"타이핑 형식을 모두 위반할 수 있습니다. 캐스트 연산자는 정적 입력을 위반합니다. 컴파일러에게 "이 표현식의 런타임 유형에 대해 더 많이 알고 있습니다"라고 말합니다. 개발자가 잘못된 경우 형식 안전성을 보호하기 위해 런타임에서 예외가 발생합니다. 개발자가 유형 안전 또는 메모리 안전을 중단하려면 "안전하지 않은"블록을 만들어 유형 안전 시스템을 끄면됩니다. 안전하지 않은 블록에서는 포인터 매직을 사용하여 int를 float (유형 안전 위반)로 취급하거나 소유하지 않은 메모리에 쓸 수 있습니다. (메모리 안전 위반)

C #에서는 컴파일 타임과 런타임에 모두 확인되는 형식 제한을 적용하여 컴파일 타임 확인이 적거나 런타임 확인이 적은 언어와 비교하여 "강력한 형식의"언어로 만듭니다. 또한 C #을 사용하면 특수한 상황에서 이러한 제한 사항에 대한 최종 실행을 수행 할 수 있으므로 이러한 최종 실행을 수행 할 수없는 언어와 비교하여 "약한 형식의"언어가됩니다.

어느 것이 진짜입니까? 말하는 것은 불가능합니다. 그것은 화자의 관점과 다양한 언어 기능에 대한 그들의 태도에 달려 있습니다.


다른 사람들이 지적했듯이, "강력한 유형"과 "약한 유형"이라는 용어는 매우 다양한 의미를 지니므로 귀하의 질문에 대한 단일 답변이 없습니다. 그러나 질문에 Perl을 구체적으로 언급했기 때문에 Perl이 약하게 입력 된 의미를 설명하려고합니다.

요점은 Perl에는 "정수 변수", "부동 변수", "문자열 변수"또는 "부울 변수"와 같은 것이 없다는 것입니다. 사실, 사용자가 (보통) 말할 수있는 한, 정수, 부동 소수점, 문자열 또는 부울 값도 없습니다 . "스칼라"만 있으면됩니다. 예를 들어 다음과 같이 쓸 수 있습니다.

$foo = "123" + "456";           # $foo = 579
$bar = substr($foo, 2, 1);      # $bar = 9
$bar .= " lives";               # $bar = "9 lives"
$foo -= $bar;                   # $foo = 579 - 9 = 570

물론, 당신이 올바르게 지적했듯이,이 모든 것은 단지 유형 강제라고 볼 수 있습니다. 그러나 요점은 Perl에서 유형은 항상 강제 된다는 것 입니다. 사실, 사용자는 변수의 내부 "유형"이 무엇인지 말하기가 매우 어렵습니다. 위의 예제에서 2 행에서 값이 $bar문자열 "9"인지 또는 숫자 9인지는 거의 의미가 없습니다. Perl에 관한 한, 그것들은 같습니다 . 실제로, 내부적으로이에 펄 스칼라에 대해서도 가능 모두 로의 경우를 예입니다, 문자열과 같은 시간에 숫자 값을 $foo줄이 후 위.

이것의 단점은 Perl 변수가 형식화되지 않았기 때문에 (또는 내부 유형을 사용자에게 노출시키지 않기 때문에) 연산자가 다른 유형의 인수에 대해 다른 작업을 수행하도록 오버로드 될 수 없다는 것입니다. "이 연산자는 숫자에 대해 X를, 문자열에 대해 Y를 수행 할 것"이라고 말할 수는 없습니다. 연산자는 인수가 어떤 종류의 값인지 알 수 없기 때문입니다.

예를 들어, Perl에는 숫자 덧셈 연산자 ( +)와 문자열 연결 연산자 ( .) 가 모두 필요합니다. 위에서 보았 듯이 문자열 ( "1" + "2" == "3") 을 추가 하거나 숫자 ( 1 . 2 == 12) 를 연결하는 것이 좋습니다. 마찬가지로, 수치 비교 연산자 ==, !=, <, >, <=, >=그리고 <=>그들의 인수의 숫자 값을 비교, 문자열 비교 연산자는 동안 eq, ne, lt, gt, le, gecmp문자열로 사전 식을 비교합니다. 그래서 2 < 10, 그러나 2 gt 10(그러나 "02" lt 10, "02" == 2). ( 자바 스크립트와 같은 다른 언어는 Perl과 같은 약한 입력을 수용하려고합니다.또한 연산자 오버로드를 수행합니다. 이것은 종종 연관성을 잃는 것과 같이 추함을 초래합니다 +.)

(여기 연고의 비행은 역사적 이유로 Perl 5에는 비트 논리 연산자와 같은 몇 가지 모퉁이가 있으며, 그 논리적 인 동작은 인수의 내부 표현에 따라 달라집니다. 일반적으로 성가신 디자인 결함으로 간주됩니다. 내부 표현은 놀라운 이유로 변경 될 수 있으므로 주어진 상황에서 해당 운영자가 수행하는 작업을 예측하는 것은 까다로울 수 있습니다.)

모든 사람이 펄이 주장 할 수, 말했다 않는 강한 유형이있다; 그들은 당신이 기대할 수있는 종류의 유형이 아닙니다. 특히, 위에서 설명한 "scalar"유형 외에도 Perl에는 "array"및 "hash"라는 두 가지 구조화 된 유형이 있습니다. 스칼라와 매우 다르며, Perl 변수 의 유형 ( 스칼라, 배열, 해시) 1을 나타내는 서로 다른 시길이 있습니다. 있습니다 당신은 그래서 이러한 유형의 사이에 강제 변환 규칙은 할 수 예를 들어, 쓰기 ,하지만 그들 중 많은 사람들이 매우 손실이 있습니다 : 예를 들어, 할당 길이 배열 로를$@%%foo = @bar$foo = @bar@bar$foo내용이 아닙니다. (또한 typeglobs 및 I / O 핸들과 같이 자주 노출되지 않는 몇 가지 이상한 유형이 있습니다.)

또한이 멋진 디자인의 약간의 단점은 특수 유형의 스칼라 (및 연산자를 사용하여 일반 스칼라와 구별 할 수 있는) 참조 유형의 존재입니다 ref. 참조를 일반 스칼라로 사용할 수 있지만 문자열 / 숫자 값은 특히 유용하지 않으며 일반 스칼라 연산을 사용하여 수정하면 특수 참조가 손실되는 경향이 있습니다. 또한 모든 Perl 변수 2bless클래스에 연결되어 해당 클래스의 객체로 바뀔 수 있습니다 . Perl의 OO 클래스 시스템은 위에서 설명한 기본 유형 (또는 유형이없는) 시스템과 다소 직교하지만 오리 입력 을 따르는 의미에서 "약한"어형 변화표. 일반적인 의견은 Perl에서 객체의 클래스를 확인하면 무언가 잘못하고 있다는 것입니다.


1 실제로, sigil은 액세스되는 값의 유형을 @foo나타내 므로 배열의 첫 번째 스칼라 가 표시 $foo[0]됩니다. 자세한 내용은 perlfaq4 를 참조하십시오.

2 Perl의 객체는 일반적으로 객체에 대한 참조를 통해 액세스되지만 실제로 얻는 bless것은 참조가 가리키는 (익명) 변수입니다. 그러나 축복은 실제로 그 가치가 아니라 변수의 속성입니다. 예를 들어, 실제 축복 변수를 다른 변수에 할당하면 변수의 얕고 축복 되지 않은 사본 만 얻게됩니다. 자세한 내용은 perlobj 를 참조하십시오.


Eric이 말한 것 외에도 다음 C 코드를 고려하십시오.

void f(void* x);

f(42);
f("hello");

Python, C #, Java 등과 같은 언어와 달리 위의 내용 유형 정보 손실 되기 때문에 약하게 입력 됩니다 . Eric은 C #에서“캐스팅을 통해 컴파일러를 우회하여“이 변수의 유형에 대해 더 많이 알고 있습니다”라고 효과적으로 지적했습니다.

그러나 그럼에도 불구하고 런타임은 여전히 ​​유형을 검사합니다! 캐스트가 유효하지 않으면 런타임 시스템이 캐스트를 포착하여 예외를 처리합니다.

유형 삭제를 사용하면 이런 일이 발생하지 않습니다. 유형 정보가 삭제됩니다. void*C 로의 캐스트 는 정확히 그렇게합니다. 이와 관련하여 위의 내용은와 같은 C # 메서드 선언과 근본적으로 다릅니다 void f(Object x).

기술적으로 C #에서는 안전하지 않은 코드 나 마샬링을 통해 형식을 지울 수도 있습니다.

이것은 약한 유형입니다. 다른 모든 정적 대의 동적 유형 검사, 즉 시간의 문제이다 타입이 선택된다.


강력한 타이핑 위키피디아 기사 에서 완벽한 예를 들어 보자 .

일반적으로 강력한 타이핑은 프로그래밍 언어가 발생할 수있는 혼합에 심각한 제한을 두는 것을 의미합니다.

약한 타이핑

a = 2
b = "2"

concatenate(a, b) # returns "22"
add(a, b) # returns 4

강력한 타이핑

a = 2
b = "2"

concatenate(a, b) # Type Error
add(a, b) # Type Error
concatenate(str(a), b) #Returns "22"
add(a, int(b)) # Returns 4

타이핑 언어가 약하면 오류없이 여러 유형을 혼합 할 수 있습니다. 강력한 형식 언어를 사용하려면 입력 형식이 예상 형식이어야합니다. 강력한 유형의 언어에서 유형을 변환 ( str(a)정수를 문자열로 변환)하거나 캐스트 ( int(b)) 할 수 있습니다.

이것은 모두 타이핑 해석에 달려 있습니다.


다른 사람들이 의견을 밝히고 의견을 밝히면서 주제에 대한 저 자신의 연구와의 토론에 기여하고 싶습니다. 나는 그들의 답변을 읽고 그들의 참조를 따르고 흥미로운 정보를 찾았습니다. 제안 된 바와 같이,이 중 대부분은 실제적인 것보다 이론적 인 것으로 보이므로 프로그래머 포럼에서 더 잘 논의 될 가능성이 높습니다.

이론적 인 관점에서 Luca Cardelli와 Peter Wegner의 기사에서 유형 이해, 데이터 추상화 및 다형성에 관한 기사 는 내가 읽은 최고의 주장 중 하나라고 생각합니다.

유형은 기본 유형화되지 않은 표현을 임의적이거나 의도하지 않은 사용으로부터 보호하는 옷 세트 (또는 갑옷)로 볼 수 있습니다 . 기본 표현을 숨기고 객체가 다른 객체와 상호 작용하는 방식을 제한하는 보호 덮개를 제공합니다. 형식화되지 않은 시스템에서 지정되지 않은 객체는 알몸 모두가 볼 수 있도록 기본 표현이 노출되도록한다. 유형 시스템을 위반하는 것은 보호 복 세트를 제거하고 알몸으로 직접 작업하는 것을 포함합니다.

이 문장은 약한 타이핑으로 유형의 내부 구조에 액세스하여 다른 유형 (다른 유형) 인 것처럼 조작 할 수 있다고 제안합니다. 안전하지 않은 코드 (Eric에서 언급 한) 또는 Konrad에서 언급 한 c 유형의 지워진 포인터로 수행 할 수있는 작업 일 수 있습니다.

기사는 계속됩니다 ...

모든식이 형식이 일치 하는 언어를 강력한 형식의 언어라고합니다. 언어가 강력하게 형식화 된 경우 컴파일러는 허용되는 프로그램이 형식 오류없이 실행되도록 보장 할 수 있습니다. 일반적으로 강력한 타이핑을 위해 노력하고 가능할 때마다 정적 타이핑을 채택해야합니다. 정적으로 유형이 지정된 모든 언어는 강력하게 유형이 지정되지만 그 반대의 경우는 아닙니다.

따라서 강력한 타이핑은 유형 오류가 없음을 의미하며, 약한 타이핑은 반대로 유형 오류가 있음을 의미한다고 가정 할 수 있습니다. 런타임 또는 컴파일 타임? 여기에 관련이없는 것 같습니다.

이 정의에 따르면 Perl과 같은 강력한 유형 강제 변환을 사용하는 언어는 시스템이 실패하지 않기 때문에 강력하게 유형화 된 것으로 간주되지만 유형을 적절하고 잘 정의 된 동등성으로 강제 처리하여 유형을 처리합니다.

반면에, 나는의 수당보다 말할 수 ClassCastExceptionArrayStoreException(자바)와 InvalidCastException, ArrayTypeMismatchException컴파일시에 적어도 약하게 입력의 수준을 나타냅니다 (C #에서)? 에릭의 대답은 이것에 동의하는 것 같습니다.

Luca Cardelli는이 질문에 대한 답변 중 하나에 제공된 참고 문헌 중 하나에서 제공되는 Typeful Programming 이라는 두 번째 기사 에서 유형 위반의 개념을 탐구합니다.

Most system programming languages allow arbitrary type violations, some indiscriminately, some only in restricted parts of a program. Operations that involve type violations are called unsound. Type violations fall in several classes [among which we can mention]:

Basic-value coercions: These include conversions between integers, booleans, characters, sets, etc. There is no need for type violations here, because built-in interfaces can be provided to carry out the coercions in a type-sound way.

As such, type coercions like those provided by operators could be considered type violations, but unless they break the consistency of the type system, we might say that they do not lead to a weakly typed system.

Based on this neither Python, Perl, Java or C# are weakly typed.

Cardelli mentions two type vilations that I very well consider cases of truly weak typing:

Address arithmetic. If necessary, there should be a built-in (unsound) interface, providing the adequate operations on addresses and type conversions. Various situations involve pointers into the heap (very dangerous with relocating collectors), pointers to the stack, pointers to static areas, and pointers into other address spaces. Sometimes array indexing can replace address arithmetic. Memory mapping. This involves looking at an area of memory as an unstructured array, although it contains structured data. This is typical of memory allocators and collectors.

This kind of things possible in languages like C (mentioned by Konrad) or through unsafe code in .Net (mentioned by Eric) would truly imply weakly typing.

I believe the best answer so far is Eric's, because the definition of this concepts is very theoretical, and when it comes to a particular language, the interpretations of all these concepts may lead to different debatable conclusions.


Weak typing does indeed mean that a high percentage of types can be implicitly coerced, attempting to guess what the coder intended.

Strong typing means that types are not coerced, or at least coerced less.

Static typing means your variables' types are determined at compile time.

Many people have recently been confusing "manifestly typed" with "strongly typed". "Manifestly typed" means that you declare your variables' types explicitly.

Python is mostly strongly typed, though you can use almost anything in a boolean context, and booleans can be used in an integer context, and you can use an integer in a float context. It is not manifestly typed, because you don't need to declare your types (except for Cython, which isn't entirely python, albeit interesting). It is also not statically typed.

C and C++ are manifestly typed, statically typed, and somewhat strongly typed, because you declare your types, types are determined at compile time, and you can mix integers and pointers, or integers and doubles, or even cast a pointer to one type into a pointer to another type.

Haskell is an interesting example, because it is not manifestly typed, but it's also statically and strongly typed.


The strong <=> weak typing is not only about the continuum on how much or how little of the values are coerced automatically by the language for one datatype to another, but how strongly or weakly the actual values are typed. In Python and Java, and mostly in C#, the values have their types set in stone. In Perl, not so much - there are really only a handful of different valuetypes to store in a variable.

Let's open the cases one by one.


Python

In Python example 1 + "1", + operator calls the __add__ for type int giving it the string "1" as an argument - however, this results in NotImplemented:

>>> (1).__add__('1')
NotImplemented

Next, the interpreter tries the __radd__ of str:

>>> '1'.__radd__(1)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'str' object has no attribute '__radd__'

As it fails, the + operator fails with the the result TypeError: unsupported operand type(s) for +: 'int' and 'str'. As such, the exception does not say much about strong typing, but the fact that the operator + does not coerce its arguments automatically to the same type, is a pointer to the fact that Python is not the most weakly typed language in the continuum.

On the other hand, in Python 'a' * 5 is implemented:

>>> 'a' * 5
'aaaaa'

That is,

>>> 'a'.__mul__(5)
'aaaaa'

The fact that the operation is different requires some strong typing - however the opposite of * coercing the values to numbers before multiplying still would not necessarily make the values weakly typed.


Java

The Java example, String result = "1" + 1; works only because as a fact of convenience, the operator + is overloaded for strings. The Java + operator replaces the sequence with creating a StringBuilder (see this):

String result = a + b;
// becomes something like
String result = new StringBuilder().append(a).append(b).toString()

This is rather an example of very static typing, without no actual coercion - StringBuilder has a method append(Object) that is specifically used here. The documentation says the following:

Appends the string representation of the Object argument.

The overall effect is exactly as if the argument were converted to a string by the method String.valueOf(Object), and the characters of that string were then appended to this character sequence.

Where String.valueOf then

Returns the string representation of the Object argument. [Returns] if the argument is null, then a string equal to "null"; otherwise, the value of obj.toString() is returned.

Thus this is a case of absolutely no coercion by the language - delegating every concern to the objects itself.


C#

According to the Jon Skeet answer here, operator + is not even overloaded for the string class - akin to Java, this is just convenience generated by the compiler, thanks to both static and strong typing.


Perl

As the perldata explains,

Perl has three built-in data types: scalars, arrays of scalars, and associative arrays of scalars, known as "hashes". A scalar is a single string (of any size, limited only by the available memory), number, or a reference to something (which will be discussed in perlref). Normal arrays are ordered lists of scalars indexed by number, starting with 0. Hashes are unordered collections of scalar values indexed by their associated string key.

Perl however does not have a separate data type for numbers, booleans, strings, nulls, undefineds, references to other objects etc - it just has one type for these all, the scalar type; 0 is a scalar value as much as is "0". A scalar variable that was set as a string can really change into a number, and from there on behave differently from "just a string", if it is accessed in a numerical context. The scalar can hold anything in Perl, it is as much the object as it exists in the system. whereas in Python the names just refers to the objects, in Perl the scalar values in the names are changeable objects. Furthermore, the Object Oriented Type system is glued on top of this: there are just 3 datatypes in perl - scalars, lists and hashes. A user defined object in Perl is a reference (that is a pointer to any of the 3 previous) blessed to a package - you can take any such value and bless it to any class at any instant you want.

Perl even allows you to change the classes of values at whim - this is not possible in Python where to create a value of some class you need to explicitly construct the value belonging to that class with object.__new__ or similar. In Python you cannot really change the essence of the object after the creation, in Perl you can do much anything:

package Foo;
package Bar;

my $val = 42;
# $val is now a scalar value set from double
bless \$val, Foo;
# all references to $val now belong to class Foo
my $obj = \$val;
# now $obj refers to the SV stored in $val
# thus this prints: Foo=SCALAR(0x1c7d8c8)
print \$val, "\n"; 
# all references to $val now belong to class Bar
bless \$val, Bar;
# thus this prints Bar=SCALAR(0x1c7d8c8)
print \$val, "\n";
# we change the value stored in $val from number to a string
$val = 'abc';
# yet still the SV is blessed: Bar=SCALAR(0x1c7d8c8)
print \$val, "\n";
# and on the course, the $obj now refers to a "Bar" even though
# at the time of copying it did refer to a "Foo".
print $obj, "\n";

thus the type identity is weakly bound to the variable, and it can be changed through any reference on the fly. In fact, if you do

my $another = $val;

\$another does not have the class identity, even though \$val will still give the blessed reference.


TL;DR

There are much more about weak typing to Perl than just automatic coercions, and it is more about that the types of the values themselves are not set into stone, unlike the Python which is dynamically yet very strongly typed language. That python gives TypeError on 1 + "1" is an indication that the language is strongly typed, even though the contrary one of doing something useful, as in Java or C# does not preclude them being strongly typed languages.


I like @Eric Lippert's answer, but to address the question - strongly typed languages typically have explicit knowledge of the types of variables at each point of the program. Weakly typed languages do not, so they can attempt to perform an operation that may not be possible for a particular type. It think the easiest way to see this is in a function. C++:

void func(string a) {...}

The variable a is known to be of type string and any incompatible operation will be caught at compile time.

Python:

def func(a)
  ...

The variable a could be anything and we can have code that calls an invalid method, which will only get caught at runtime.


As many others have expressed, the entire notion of "strong" vs "weak" typing is problematic.

As a archetype, Smalltalk is very strongly typed -- it will always raise an exception if an operation between two objects is incompatible. However, I suspect few on this list would call Smalltalk a strongly-typed language, because it is dynamically typed.

I find the notion of "static" versus "dynamic" typing more useful than "strong" versus "weak." A statically-typed language has all the types figured out at compile-time, and the programmer has to explicitly declare if otherwise.

Contrast with a dynamically-typed language, where typing is performed at run-time. This is typically a requirement for polymorphic languages, so that decisions about whether an operation between two objects is legal does not have to be decided by the programmer in advance.

In polymorphic, dynamically-typed languages (like Smalltalk and Ruby), it's more useful to think of a "type" as a "conformance to protocol." If an object obeys a protocol the same way another object does -- even if the two objects do not share any inheritance or mixins or other voodoo -- they are considered the same "type" by the run-time system. More correctly, an object in such systems is autonomous, and can decide if it makes sense to respond to any particular message referring to any particular argument.

Want an object that can make some meaningful response to the message "+" with an object argument that describes the colour blue? You can do that in dynamically-typed languages, but it is a pain in statically-typed languages.

참고 URL : https://stackoverflow.com/questions/9929585/seeking-clarification-on-apparent-contradictions-regarding-weakly-typed-language

반응형