Merged PR
- Fix set test_merge_and_mutate
Fix set test_merge_and_mutate by tgsong827 · Pull Request #3935 · RustPython/RustPython
fix #3866 make function update_internal() check AnySet Type check Dict Type
github.com
개요
set.update()
함수는 인자로 set
타입과 dict
타입도 받을 수 있는데,
이 경우 인자로 넘어온 set
과 dict
타입이 담고 있는 객체가 무엇이냐에 따라 update 도중 Iteration의 사이즈가 변할 수 있습니다.
CPython에서는 update의 인자로 들어온 iterable 객체가 set
타입인지 dict
타입인지 검사하고,
각 케이스에 맞춰 update 로직을 처리하고 있습니다.
RustPython에는 이 두 타입에 대한 처리 로직이 아직 구현되지 않아 발생한 문제로,
이 두 타입에 대한 검사와 처리 로직을 추가해 문제를 해결했습니다.
과정
원인 분석
RustPython set.update()
함수는 인자로 들어온 iterable 객체가 set
타입인지 dict
타입인지 검사하는 로직이 아직 구현되어있지 않았습니다.
따라서 iteration이 도는 동안 set
자체의 사이즈가 변하는 에러가 발생했습니다.
수정
먼저 PySetInner
에 구현된 update()
함수는 다른 연산에도 사용되는 케이스이기 때문에
[pymethod]update()
연산에 사용될 update_internal()
함수를 구현했습니다.
update_internal()
함수에는 set
과 dict
타입 검사 분기가 구현되어 있고,
각 케이스에 따라 update를 위한 merge_set()
과 merge_dict()
함수를 추가했습니다.
update_internal()
에서 set
타입 검사를 위해 AnySet
구조체로 변환한 결과가 merge_set()
함수의 인자 값으로 들어옵니다.
AnySet
구조체는 set
과 frozen_set
두 가지 타입을 담을 수 있습니다.any_set
이 갖고 있는 요소들을 구하기 위해선 set
또는 frozen_set
으로 변환이 필요했고, 이를 위해 as_inner()
함수를 구현했습니다.
as_inner()
함수에서 PySetInner
를 구할 수 있고,
이를 통해 set
타입이 갖고 있는 elements
를 가져와 각 item을 추가하도록 update 함수를 구현했습니다.
- 테스트 코드
test_set.py →test_merge_and_mutate
결과적으로, 해당 이슈의 테스트 케이스를 통과할 수 있게 됐고, CI도 정상적으로 통과되어 Merge 될 수 있었습니다.
'Dev > Contribution' 카테고리의 다른 글
[RustPython] fcntl.ioctl 수정하기 (1) | 2022.09.01 |
---|---|
[RustPython] traceback.tb_next mutable 하게 만들기 (0) | 2022.08.21 |
[RustPython] sslError 클래스에 library, reason 속성 추가하기 (0) | 2022.08.19 |
[RustPython] StopIteration 수정하기 (0) | 2022.08.07 |