Skip to content

Commit 90fac6e

Browse files
Optimize is_successful
The optimization achieves a **13% runtime improvement** by replacing the dynamic `isinstance(self, Success)` check with static method overrides. **Key Changes:** - `Result.is_successful()` now returns `False` directly instead of checking `isinstance(self, Success)` - `Success.is_successful()` overrides the base method to return `True` directly **Why This Is Faster:** The original code performed a runtime type check (`isinstance(self, Success)`) on every call, which requires: 1. Walking the method resolution order (MRO) 2. Comparing against the Success class 3. Returning the boolean result The optimized version leverages Python's method dispatch mechanism, which happens once during attribute lookup. When `is_successful()` is called, Python's vtable-like dispatch directly invokes the appropriate override (`Success.is_successful()` or `Result.is_successful()`), eliminating the per-call isinstance overhead. **Performance Impact by Test Case:** - **Failure instances**: 47.8-57.5% faster - Biggest wins as these frequently checked failure paths no longer need isinstance checks - **Success instances**: 4.3-21.7% faster - Still improved by avoiding isinstance overhead - **Base Result instances**: 21.7-29.6% faster - Now returns False immediately instead of checking type - **Large-scale tests**: Consistent 8-21% improvements across 500-1000 iterations, showing the optimization scales well **Workload Impact:** Based on function_references, `is_successful()` is called extensively in test detection and optimization workflows (`test_unused_helper_revert.py`). Since the function appears in critical path testing logic where many Result objects are checked for success/failure status, this optimization provides meaningful improvements to CI/CD and development iteration times. The method is particularly beneficial in loops and bulk operations where thousands of calls accumulate (as demonstrated by the large-scale test showing consistent speedups at 1000 instances). The optimization maintains identical semantics - subclass polymorphism is preserved, all test cases pass with the same boolean results, and the API remains unchanged.
1 parent 12ff3f4 commit 90fac6e

1 file changed

Lines changed: 3 additions & 1 deletion

File tree

codeflash/either.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ def is_failure(self) -> bool:
1414
return isinstance(self, Failure)
1515

1616
def is_successful(self) -> bool:
17-
return isinstance(self, Success)
17+
return False
1818

1919
def unwrap(self) -> L | R:
2020
if self.is_failure():
@@ -35,6 +35,8 @@ class Failure(Result[L, R]):
3535

3636
class Success(Result[L, R]):
3737
pass
38+
def is_successful(self) -> bool:
39+
return True
3840

3941

4042
def is_successful(result: Result[L, R]) -> bool:

0 commit comments

Comments
 (0)