파이썬에서 범위와 네임 스페이스 사이의 관계는 무엇입니까?


12

많은 자원에서 "scope" 와 "namespaces" 는 서로 바꿔서 사용되는 것으로 나타났습니다 .

  • 범위는 이름을 사용할 수있는 코드 영역을 정의합니다.
  • LEGB 규칙은 이름을 찾는 방법을 정의합니다.
  • 네임 스페이스는 이름을 찾는 곳입니다.

그런 다음 읽었습니다.

  • "이름은 할당 된 위치에 따라 네임 스페이스에 바인드됩니다 ..." (어휘 범위의 범위를 다루는 것이라고 생각합니다).
  • "함수는 프로그램에 네임 스페이스 레이어를 추가합니다" [ ref. ] (추가 로컬 범위를 추가하지 않습니까?)
  • "함수 정의 내에 지정된 모든 이름은 로컬 범위 (함수 호출과 연관된 네임 스페이스)에 있습니다."
  • "글로벌 스코프 — 즉, 변수가 모듈 파일의 최상위 레벨에서 작성 (할당) 된 네임 스페이스입니다."

* 모든 인용문은 Python 5th edition ch17을 학습 한 것입니다.

파이썬의 네임 스페이스는 범위가 구현되는 방식입니까? 그들은 같은 것입니까? 누구든지 나를 밝힐 수 있습니까?


1
따옴표에 대한 참조를 제공 할 수 있습니까? 하나는 찾을 수 있지만 다른 것은 찾을 수 없습니다.
— jonrsharpe

1
네임 스페이스는 한 가지 유형의 범위입니다. 참조 stackoverflow.com/questions/291978/...
— 로버트 하비

답변:


16

네임 스페이스는 값이 문자열로 이름을 매핑, 사전이다. 과 같은 할당을 수행하면 a = 1네임 스페이스가 변경됩니다. 와 같이 참조 할 때 print(a)Python은 네임 스페이스 목록을 살펴보고 이름이 키 인 네임 스페이스를 찾습니다.

범위 네임 스페이스와 어떤 순서로보고됩니다 정의합니다. 임의의 기준 범위는 항상 로컬 공간에서 시작하고,이 이동하기 전에, 모듈의 글로벌 네임에 도달 할 때까지 바깥쪽으로 이동 builtins(스페이스 해당 참조 파이썬 소정 기능 및 상수 등을 range하고 getattr) 라인의 단부이며 .

라는 이름의 기능이 상상 inner이라는 이름의 전역 함수 내에 중첩을, outer그리고 inner이름에 대한 참조를 포함합니다. 파이썬은 먼저 inner네임 스페이스를 찾습니다 . 이름이 없으면 Python은 outer네임 스페이스 를 찾습니다 . 그것이 실패하면, 파이썬은 모듈의 global네임 스페이스를 시도하고 , builtin네임 스페이스를 NameError찾지 못하면 결국 이름을 찾을 수 없게됩니다.

우리가 말할 때 x함수의 네임 스페이스에, 우리는이 로컬 함수 내에서,이 정의 의미한다. x함수의 범위 안에 있다고 x하면 함수의 네임 스페이스 또는 함수의 네임 스페이스가 중첩 된 외부 네임 스페이스에 있다는 의미입니다.

함수를 정의 할 때마다 새로운 네임 스페이스와 범위를 만듭니다. 네임 스페이스는 새로운 로컬 이름 해시입니다. 범위는 새 네임 스페이스에서 시작하여 외부 네임 스페이스 (외부 범위), 전역 네임 스페이스 (전역 범위) 및 내장에 이르는 방식으로 작동합니다.

이 용어는 거의 상호 교환 적으로 사용될 수 있지만 같은 의미이기 때문이 아닙니다. 그들이 의미하는 바에서 그것들이 많이 겹치기 때문입니다.


3
"이 용어들은 거의 상호 교환 가능하게 사용될 수 있지만, 그것은 같은 의미를 갖기 때문이 아니라, 그들이 의미하는 바와 많이 중복되기 때문입니다."
— Nikos

2
이 답변은 정신적으로는 정확하지만 세부적으로 잘못되었습니다. Python의 클래스에는 새로운 네임 스페이스가 도입되지 않으므로 클래스 속성이 클래스 이름으로 규정되어야하고 인스턴스 속성이 인스턴스 이름으로 규정되어야합니다. 내부에서 외부로 파이썬에서 네임 스페이스의 레벨은 로컬, 엔 클로징, 글로벌 및 내장입니다. 클래스는이 레벨 중 어느 하나에서 정의 될 수 있지만 클래스 멤버는 항상 자격을 갖추어야합니다.
— Rob Smallshire

네가 옳아. 수업은 내가 말한 방식대로 작동하지 않습니다. 나는 그들이 함수와 같은 어휘 범위를 생성한다고 생각했지만 그렇지 않습니다. 시간이 있으면 답변을 업데이트하십시오. 그렇지 않으면 언젠가 할 것입니다. 감사.
— Carl Smith

1
+1 화려한 미묘함을 경제적으로 캡슐화하여 훌륭한 답변. 나는 이것이 매우 도움이된다는 것을 알았습니다. 감사합니다!
— 시커

1
"네임 스페이스는 이름, 값 쌍의 해시이며 파이썬 사전과 비슷합니다."-네임 스페이스 는 파이썬 사전 으로 저장되어 있습니다. 예를 들어, globals ()를 호출하여 전역 네임 스페이스를 편집 할 수 있습니다. 전역을 사용하여 사전을 직접 수정하여 객체와 이름을 바인딩 할 수 있습니다 (예 : globals () [name] = "object"). 그렇지 않으면 큰 대답입니다.
— Evan Rosica

4

여기 에 파이썬 네임 스페이스에 대한 훌륭한 기사가 있습니다 . 범위와 네임 스페이스 간의 참조에 대한 질문에 답변하기 위해 관련 부분을 인용하려면 다음을 수행하십시오.

범위는 접두사없이 네임 스페이스에 액세스 할 수있는 프로그램 영역을 나타냅니다.

예를 들어, 간단한 다이 롤링 프로그램을 상상해보십시오.

import random  # 'random' is in module namespace

def roll(sides=6):  # 'roll' is in module namespace, 'sides' is in roll's
    return random.randint(1, sides)  # both 'random' and 'sides' are in scope here

# but sides can't be accessed out here 

roll 자체 네임 스페이스 가 있지만 모듈 네임 스페이스의 이름 도 scope에 있습니다.


@CarlSmith는 초기 파이썬 문서에서 다음과 같이 말합니다. "스코프는 네임 스페이스에 직접 액세스 할 수있는 Python 프로그램의 텍스트 영역입니다. 여기서"직접 액세스 가능 "은 이름에 대한 규정되지 않은 참조가 이름을 찾으려고 함을 의미합니다. 이름 공간에서. "
— jonrsharpe

@CarlSmith는 비 로컬 / 클로징 범위의 추가를 제외하고는 많이 바뀌 었습니까? 네임 스페이스에 이름과 값이 포함되어 있고 스코프가 액세스 할 수있는 네임 스페이스를 알려줍니다.
— jonrsharpe

예전 의견을 삭제했습니다.
— Carl Smith
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.