-
Notifications
You must be signed in to change notification settings - Fork 34
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
Generating Num (SBV a)
instances "generically"
#698
Comments
It seems like boardVal :: Integer -> Board -> SBV (Integer, Integer)
boardVal i = sum . concat . map (map (squareVal i)) However, in an other example I have used |
Indeed, here is an shrinking to a use of import Data.SBV
type Val = (Integer, Integer)
instance Num Val where
fromInteger i = (i, 0)
negate (x, y) = (negate x, negate y)
(x1, y1) + (x2, y2) = (x1 + x2, y1 + y2)
(*) = undefined
abs = undefined
signum = undefined
type SVal = SBV Val
valVec :: Int -> Symbolic [SVal]
valVec n = mapM (\ k -> symbolic ("X" ++ show k)) [0..n-1]
main = satWith z3{ verbose = True } $ do
v <- valVec 3
pure $ sum v .== 1 |
This is my final shrinking, to just a use of import Data.SBV
type Val = (Integer, Integer)
instance Num Val where
fromInteger i = (i, 0)
(x1, y1) + (x2, y2) = (x1 + x2, y1 + y2)
(*) = undefined
abs = undefined
negate = undefined
signum = undefined
main = satWith z3{ verbose = True } $ do
x :: SBV Val <- symbolic "x"
y :: SBV Val <- symbolic "y"
pure $ x + y .== 1 |
TODO: need to ensure that areas are connected
Hi Andreas, This is essentially a duplicate of #598 The main problem here is once you lift a value to an SBV level like you did with import Data.SBV
import Data.SBV.Tuple
type Val = (Integer, Integer)
instance Num Val where
fromInteger i = (i, 0)
(x1, y1) + (x2, y2) = (x1 + x2, y1 + y2)
(*) = undefined
abs = undefined
negate = undefined
signum = undefined
instance {-# OVERLAPPING #-} Num (SBV Val) where
fromInteger i = literal (i, 0)
v1 + v2 = tuple (v1^._1 + v2^._1, v1^._2 + v2^._2)
(*) = undefined
abs = undefined
negate = undefined
signum = undefined
main = sat $ do
x :: SBV Val <- symbolic "x"
y :: SBV Val <- symbolic "y"
pure $ x + y .== 1 When I run this, I get: *Main> main
Satisfiable. Model:
x = (0,0) :: (Integer, Integer)
y = (1,0) :: (Integer, Integer) which is what you were expecting in the first place. Now, I do agree that this is rather "esoteric" and requires a deeper understanding of how SBV lifts values. And perhaps there's a way to simplify the user experience here. I'd love to hear what you think to make it easier to use. Bottom line: This is an unfortunate consequence of how arbitrary liftings work in SBV, and while I'd like to make it better, it is behaving as designed, as crappy as that design is. |
Hello Levent, thank you for your quick answer and the explanation. Maybe the Would it make sense to restrict this instance to the types where it works correctly? E.g. I would have gotten an error "no instance for Lines 1322 to 1329 in 720255d
(Due to limited expressivity of the Haskell class system, this would probably lead to tons of boilerplate...) |
Thanks Andreas.. You're absolutely right that The other difficulty is that the I'm open to enhancements here. Ideas/explorations/Pull-Requests are most welcome. |
I think we can close this ticket. I captured the exploration of removal of the |
Hi Andreas, As of 9a90e88 the following program now gives a type error: import Data.SBV
type Val = (Integer, Integer)
instance Num Val where
fromInteger i = (i, 0)
(x1, y1) + (x2, y2) = (x1 + x2, y1 + y2)
(*) = undefined
abs = undefined
negate = undefined
signum = undefined
main = sat $ do
x :: SBV Val <- symbolic "x"
y :: SBV Val <- symbolic "y"
pure $ x + y .== 1 yielding:
This is indeed better; thanks for noting that the general To "fix" this, one needs to write: import Data.SBV.Tuple
instance Num (SBV Val) where
fromInteger i = literal (i, 0)
v1 + v2 = let (x1, y1) = untuple v1
(x2, y2) = untuple v2
in tuple (x1+x2, y1+y2)
(*) = undefined
abs = undefined
negate = undefined
signum = undefined And the program will work as expected. I'm curious if we can make this "easier." Clearly the I played around with the You're an expert in generic programming; is there a solution to "mimic" a given instance (i.e., |
Num (SBV a)
instances "generically"
Thanks for further digging into this issue @LeventErkok.
You are flattering me. :-) |
Yeah, I was thinking about it myself and there doesn't seem to be an easy way to do this to lift an "existing" instance. Maybe via template-haskell, but I don't think the complexity is worth it. |
(This is my first attempt to use
sbv
.)I am hitting an impossible in
sbv-10.10
in the internalsh
function:The text was updated successfully, but these errors were encountered: