-
Notifications
You must be signed in to change notification settings - Fork 1
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
PoE mixing function #205
PoE mixing function #205
Conversation
Add Underflow error condition
- Uses Uint64 and StdDecimal - StdDecimal to rust_decimal::Decimal conversion
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am happy to merge this as is.
It sets up the framework for user-configurable curves quite well.
It also proves the potential of using decimal power and exponents (very nice).
I mention a few minor cleanup items that can be addressed in a future PR.
Other points that would be interesting to me would be:
- Implement some variant of the your comment using
x / sqrt(x^2 + 1)
as the sigmoid curve (where x is some function of stake and engagement) - Some gas benchmarks of these various approaches. We just need wasm gas benchmarks, so no need to run multiple runs (criteria) but rather one test case that runs in a vm and records gas. This would be similar to the integration tests in cosmwasm/contracts
Note: I cannot import cosmwasm-vm on my Mac m1, so it would be nice to make that whole dependency optional under some feature flag.
assert_eq!(err, ContractError::ComputationOverflow("powd")); | ||
|
||
// Precise limit | ||
let very_big = 32_313_447; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmmm... this is a good limit to document.
It would be good to test with some reasonable numbers.
Note that stake is measured in utgd. We could expect maybe 5 million TGD (5% of tokens) as an extreme case.
This would be 5_000_000_000_000 stake (much bigger than the limit).
On the other hand, we will have maybe 1 million engagement total, so let's say 5_000 engagement as a high value.
Basically, it would be an interesting tests to see the maximum stake that we can not overflow with 5_000 engagement.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's just this number squared, divided by 5_000, i.e. 208_831_771_404. Which is not enough, according to your comment above. We can perhaps convert / down-scale to TGD
(or mTGD
) first, and then it will suffice.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Okay, just add a FIXME comment there and I will think of this
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Bad news, the number is exactly the same (32_313_447) because what is overflowing is powd
. That said, powd
is not very robust / smart, because a number raised to an exponent smaller than 1 will always be smaller than the number(!).
So, this looks like a flaw / limitation in powd
's implementation. I'll open an issue in rust_decimal
, to see what can be done about it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This actually has a couple simple solutions:
Use an exponent p = 1/2 instead of p = 0.68. This can be implemented usingDone in theDecimal::sqrt()
(which doesn't suffer from this problem); or even,integer_sqrt()
.SigmoidSqrt
impl.- stake = 32_313_447 and engagement = 5_000 already produces a saturating reward (1_000). So, we can add a check for numbers above these values, and return
max_r
directly. This also saves some cycles, and extends the range up tou63::MAX
for both factors. This can be done, but requires some care to detect when a particular parametrization saturates.
Will do.
OK. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for adding all those curves and tests
Closes #9.
TODO:
validate()
method.Algebraic sigmoid.(Done inAlgebraicSigmoid
)Sigmoid-like with exponent p = 1/2.(Done inSigmoidSqrt
)