Bridging the gap between logic and functional programming