ANTLR4 grammar which accepts list of optional and required arguments in any order - antlr

How can I write an ANTLR rule that accepts a mixture of optional and required arguments in any order?
For example, a valid query could look like function(a = 5, c = "foo", b = 21) or function(b = 4, c = 5) where a is optional but c and b are required. The only valid arguments are a, b and c.
Any help would be appreciated.

That is not something you would define in your grammar. The grammar would just accept function(a = 5, c = "foo", b = 21) and function(a = 5, c = "foo", i = 21). After parsing the input, you would reject the latter example in a traversal of the parse tree.
For example, take the BNF specification of a Java assignment statement:
Expression:
Expression1 [AssignmentOperator Expression1]
where Expression1 might very well be the variable Q which is defined as follows:
final int Q = 42;
In other words: the statement Q = 123; would be illegal since it was already defined final. Such semantic checks are not defined in the grammar but handled at a later stage.

Related

What are the differences between the unary minus and unary tilde minus operators in ocaml?

I'm learning OCaml, and the docs and books I'm reading aren't very clear on some things.
In simple words, what are the differences between
-10
and
~-10
To me they seem the same. I've encountered other resources trying to explain the differences, but they seem to explain in terms that I'm not yet familiar with, as the only thing I know so far are variables.
In fact, - is a binary operator, so some expression can be ambigous : f 10 -20 is treated as (f 10) - 20. For example, let's imagine this dummy function:
let f x y = (x, y)
If I want produce the tuple (10, -20) I naïvely would write something like that f 10 -20 which leads me to the following error:
# f 10 -20;;
Error: This expression has type 'a -> int * 'a
but an expression was expected of type int
because the expression is evaluated as (f 10) - 20 (so a substract over a function!!) so you can write the expression like this: f 10 (-20), which is valid or f 10 ~-20 since ~- (and ~+ and ~-. ~+. for floats) are unary operators, the predecense is properly respected.
It is easier to start by looking at how user-defined unary (~-) operators work.
type quaternion = { r:float; i:float; j:float; k:float }
let zero = { r = 0.; i = 0.; j = 0.; k = 0. }
let i = { zero with i = 1. }
let (~-) q = { r = -.q.r; i = -.q.i; j = -. q.j; k = -. q.k }
In this situation, the unary operator - (and +) is a shorthand for ~- (and ~+) when the parsing is unambiguous. For example, defining -i with
let mi = -i
works because this - could not be the binary operator -.
Nevertheless, the binary operator has a higher priority than the unary - thus
let wrong = Fun.id -i
is read as
let wrong = (Fun.id) - (i)
In this context, I can either use the full form ~-
let ok' = Fun.id ~-i
or add some parenthesis
let ok'' = Fun.id (-i)
Going back to type with literals (e.g integers, or floats), for those types, the unary + and - symbol can be part of the literal itself (e.g -10) and not an operator. For instance redefining ~- and ~+ does not change the meaning of the integer literals in
let (~+) = ()
let (~-) = ()
let really = -10
let positively_real = +10
This can be "used" to create some quite obfuscated expression:
let (~+) r = { zero with r }
let (+) x y = { r = x.r +. y.r; i = x.i +. y.i; k = x.k +. x.k; j =x.k +. y.j }
let ( *. ) s q = { r = s *. q.r; i = s *. q.i; j = s *. q.j; k = s *. q.k }
let this_is_valid x = +x + +10. *. i
OCaml has two kinds of operators - prefix and infix. The prefix operators precede expressions and infix occur in between the two expressions, e.g., in !foo we have the prefix operator ! coming before the expression foo and in 2 + 3 we have the infix operator + between expressions 2 and 3.
Operators are like normal functions except that they have a different syntax for application (aka calling), whilst functions are applied to an arbitrary number of arguments using a simple syntax of juxtaposition, e.g., f x1 x2 x3 x41, operators can have only one (prefix) or two (infix) arguments. Prefix operators are very close to normal functions, cf., f x and !x, but they have higher precedence (bind tighter) than normal function application. Contrary, the infix operators, since they are put between two expressions, enable a more natural syntax, e.g., x + y vs. (+) x y, but have lower precedence (bind less tight) than normal function application. Moreover, they enable chaining several operators in a row, e.g., x + y + z is interpreted as (x + y) + z, which is much more readable than add (add (x y) z).
Operators in OCaml distinguished purely syntactically. It means that the kind of an operator is fully defined by the first character of that operator, not by a special compiler directive, like in some other languages (i.e., there is not infix + directive in OCaml). If an operator starts with the prefix-symbol sequence, e.g., !, ?#, ~%, it is considered as prefix and if it starts with an infix-symbol then it is, correspondingly, an infix operator.
The - and -. operators are treated specially and can appear both as prefix and infix. E.g., in 1 - -2 we have - occurring both in the infix and prefix positions. However, it is only possible to disambiguate between the infix and the prefix versions of the - (and -.) operators when they occur together with other operators (infix or prefix), but when we have a general expression, the - operator is treated as infix. E.g., max 0 -1 is interpreted as (max 0) - 1 (remember that operator has lower precedence than function application, therefore when they two appear with no parentheses then functions are applied first and operators after that). Another example, Some -1, which is interpreted as Some - 1, not as Some (-1). To disambiguate such code, you can use either the parentheses, e.g., max 0 (-1), or the prefix-only versions, e.g, Some ~-1 or max 0 ~-1.
As a matter of personal style, I actually prefer parentheses as it is usually hard to keep these rules in mind when you read the code.
1) Purists will say that functions in OCaml can have only one argument and f x1 x2 x3 x4 is just ((f x1) x2) x3) x4, which would be a totally correct statement, but a little bit irrelevant to the current discussion.

When (exactly) can equality be proposed between different types using '='?

In the documentation, it says:
Equality in Idris is heterogeneous, meaning that we can even propose
equalities between values in different types:
idris_not_php : 2 = "2"
That particular example compiles, but the hole is presented as being of type fromInteger 2 = "2". Given that fromInteger 2 can belong to any type that is an instance of Num, maybe the compiler isn't quite clever enough to deduce that the value of 2 is not a String?
In comparison, the following slightly different code fails to compile:
idris_not_php : S (S Z) = "2"
The compiler reports a type mismatch between Nat and String.
Also, the following does compile successfully:
Num String where
(+) x y = y
(*) x y = y
fromInteger n = "2"
idris_not_php : 2 = "2"
idris_not_php = the (the String 2 = "2") Refl
And these two compile:
idris_not_php : S (S Z) ~=~ "2"
idris_not_php = ?hole
two_is_two : 2 ~=~ 2
two_is_two = Refl
Is there any particular rule about when = can be used between things that are of different types, or is it just a matter of using ~=~ when = doesn't work? Are ~=~ and = semantically identical, and if so, why is ~=~ even necessary?
This answer have some theoretical notes about heterogeneous equality in Idris. And this answer has example of why you may need (~=~).
I just want to add a little about idris_not_php : 2 = "2" example. This can be type checked if you have Num instance for String type just as you did. Integral constants in Idris are polymorphic. Though, any reasonable program wouldn't have such instance for String because it doesn't make sense.

Does "<-" mean assigning a variable in Haskell?

Just started Haskell, it's said that everything in Haskell is "immutable" except IO package. So when I bind a name to something, it's always something immutable? Question, like below:
Prelude> let removeLower x=[c|c<-x, c `elem` ['A'..'Z']]
Prelude> removeLower "aseruiiUIUIdkf"
"UIUI"
So here:
1. “removeLower" is an immutable? Even it's a function object?
But I can still use "let" to assign something else to this name.
2. inside the function "c<-x" seems that "c" is a variable.
It is assigned by list x's values.
I'm using the word "variable" from C language, not sure how Haskell name all its names?
Thanks.
If you're familiar with C, think of the distinction between declaring a variable and assigning a value to it. For example, you can declare a variable on its own and later assign to it:
int i;
i = 7;
Or you can declare a variable and assign initial value at the same time:
int i = 7;
And in either case, you can mutate the value of a variable by assigning to it once more after the first initialization or assignment:
int i = 7; // Declaration and initial assignment
i = 5; // Mutation
Assignment in Haskell works exclusively like the second example—declaration with initialization:
You declare a variable;
Haskell doesn't allow uninitialized variables, so you are required to supply a value in the declaration;
There's no mutation, so the value given in the declaration will be the only value for that variable throughout its scope.
I bolded and hyperlinked "scope" because it's the second critical component here. This goes one of your questions:
“removeLower" is an immutable? Even it's a function object? But I can still use "let" to assign something else to this name.
After you bind removeLower to the function you define in your example, the name removeLower will always refer to that function within the scope of that definition. This is easy to demonstrate in the interpreter. First, let's define a function foo:
Prelude> let foo x = x + 2
Prelude> foo 4
6
Now we define an bar that uses foo:
Prelude> let bar x = foo (foo x)
Prelude> bar 4
8
And now we "redefine" foo to something different:
Prelude> let foo x = x + 3
Prelude> foo 4
7
Now what do you think happens to bar?
Prelude> bar 4
8
It remains the same! Because the "redefinition" of foo doesn't mutate anything—it just says that, in the new scope created by the "redefinition", the name foo stands for the function that adds three. The definition of bar was made in the earlier scope where foo x = x + 2, so that's the meaning that the name foo has in that definition of bar. The original value of foo was not destroyed or mutated by the "redefinition."
In a Haskell program as much as in a C program, the same name can still refer to different values in different scopes of the program. This is what makes "variables" variable. The difference is that in Haskell you can never mutate the value of a variable within one scope. You can shadow a definition, however—uses of a variable will refer to the "nearest" definition of that name in some sense. (In the case of the interpreter, the most recent let declaration for that variable.)
Now, with that out of the way, here are the syntaxes that exist in Haskell for variable binding ("assignment"). First, there's top-level declarations in a module:
module MyLibrary (addTwo) where
addTwo :: Int -> Int
addTwo x = x + 2
Here the name addTwo is declared with the given function as its value. A top level declaration can have private, auxiliary declarations in a where block:
addSquares :: Integer -> Integer
addSquares x y = squareOfX + squareOfY
where square z = z * z
squareOfX = square x
squareOfY = square y
Then there's the let ... in ... expression, that allows you to declare a local variable for any expression:
addSquares :: Integer -> Integer
addSquares x y =
let square z = z * z
squareOfX = square x
squareOfY = square y
in squareOfX + squareOfY
Then there's the do-notation that has its own syntax for declaring variables:
example :: IO ()
example = do
putStrLn "Enter your first name:"
firstName <- getLine
putStrLn "Enter your lasst name:"
lastName <- getLine
let fullName = firstName ++ " " ++ lastName
putStrLn ("Hello, " ++ fullName ++ "!")
The var <- action assigns a value that is produced by an action (e.g., reading a line from standard input), while let var = expr assigns a value that is produced by a function (e.g., concatenating some strings). Note that the let in a do block is not the same thing as the let ... in ... from above!
And finally, in list comprehension you get the same assignment syntax as in do-notation.
It's referring to the monadic bind operator >>=. You just don't need to explicitly write a lambda as right hand side parameter. The list comprension will be compiled down to the monadic actions defined. And by that it means exactly the same as in a monadic environment.
In fact you can replace the list comprension with a simple call to filter:
filter (`elem` ['A' .. 'Z']) x
To answer your question regarding the <- syntactic structure a bit clearer:
[c| c <- x]
is the same as
do c <- x
return c
is the same as
x >>= \c -> return c
is the same as
x >>= return
Consider the official documentation of Haskell for further reading: https://hackage.haskell.org/package/base-4.8.2.0/docs/Control-Monad.html#v:-62--62--61-
[c|c<-x, c `elem` ['A'..'Z']]
is a list comprehension, and c <- x is a generator where c is a pattern to be matched from the elements of the list x. c is a pattern which is successively bound to the elements of the input list x which are a, s, e, u, ... when you evaluate removeLower "aseruiiUIUIdkf".
c `elem` ['A'..'Z']
is a predicate which is applied to each successive binding of c inside the comprehension and an element of the input only appears in the output list if it passes this predicate.

How can I use a functor name like a variable in Prolog?

We have this assignment for our Prolog course. After two months of one hour per week of Prolog, it is still an enigma to me, my thinking seems unable to adapt from procedural languages - yet.
There is a knowledge base containing predicates/functors with the same name and arities 1, 2 and 3.
The call form should be
search(functor_name, argument, S).
The answers should find all occurrences with this functor name and argument, regardless of arity.
The answers should be of the form:
S = functor_name(argument);
S = functor_name(argument,_);
S = functor_name(_,argument);
S = functor_name(argument,_,_);
S = functor_name(_,argument,_);
S = functor_name(_,_,argument);
false.
I have found out that I could use call to test if the entry in the knowledge base exists.
But call does not seem to work with a variable for the functor name. I am totally baffled, no idea how to use a variable for a functor name.
UPDATE:
My question has been partly answered.
My new code gives me true and false for arities 1, 2 and 3 (see below).
search(Person,Predicate) :-
ID = Person, Key = Predicate, current_functor(Key,1),
call(Key,ID)
; ID = Person, Key = Predicate, current_functor(Key,2),
(call(Key,ID,_);call(Key,_,ID))
; ID = Person, Key = Predicate, current_functor(Key,3),
(call(Key,ID,_,_);call(Key,_,ID,_);call(Key,_,_,ID)).
UPDATE2:
Another partial answer has come in. That one gives me S as a list of terms, but the "other" arguments are placeholders:
search2(Predicate, Arg, S) :-
( Arity = 2 ; Arity = 3 ; Arity = 4 ),
functor(S, Predicate, Arity),
S =.. [_,Predicate|Args],
member(Arg, Args).
The result is quite nice. Still missing: the Predicate should not be inside the brackets and the other arguments should be taken literally from the knowledge base, not written as placeholders. The current result looks like this:
?- search2(parent,lars,S).
S = parent(parent, lars) ;
S = parent(parent, lars, _G1575) ;
S = parent(parent, _G1574, lars) ;
S = parent(parent, lars, _G1575, _G1576) ;
S = parent(parent, _G1574, lars, _G1576) ;
S = parent(parent, _G1574, _G1575, lars).
I am giving up with this question, because the question was posed in the wrong way from the beginning. I should have asked more specifically - which I could not, because I am still no good in Prolog.
#false helped me most. I am accepting his answer.
There are two approaches here, one "traditional" (1970s) that implements literally what you want:
search(F, Arg, S) :-
( N = 1 ; N = 2 ; N = 3 ), % more compactly: between(1,3, N)
functor(S, F, N),
S =.. [_|Args], % more compactly: between(1,N, I), arg(I,S,Arg)
member(Arg, Args).
The other reconsiders the explicit construction of the goal. Actually, if you have a functor F, and arguments A1, A2, A3 you can immediately write the goal call(F, A1, A2, A3) without any use of functor/3 or (=..)/2.
There are many advantages of using call(F, A1, A2, A3) in place of Goal =.. [F, A1, A2, A3], call(Goal): In many situations it is cleaner, faster, and much easier to typecheck. Further, when using a module system, the handling of potential module qualifications for F will work seamlessly. Whereas (=..)/2 will have to handle all ugly details explicitly, that is more code, more errors.
search(F,A,call(F,A)).
search(F,A,call(F,A,_)).
search(F,A,call(F,_,A)).
search(F,A,call(F,A,_,_)).
search(F,A,call(F,_,A,_)).
search(F,A,call(F,_,_,A)).
If you want to shorten this, then rather construct call/N dynamically:
search(F, Arg, S) :-
( N = 2 ; N = 3 ; N = 4 ),
functor(S, call, N),
S =.. [_,F|Args],
member(Arg, Args).
Note that call needs an extra argument for the functor F!
You can use the "univ" operator, =.., to construct a goal dynamically:
?- F=member, X=1, L=[1,2,3], Goal =.. [F, X, L], call(Goal).
F = member,
X = 1,
L = [1, 2, 3],
Goal = member(1, [1, 2, 3]) .

What's the -> operator in Prolog and how can I use it?

I've read about it in a book but it wasn't explained at all. I also never saw it in a program. Is part of Prolog syntax? What's it for? Do you use it?
It represents implication. The righthand side is only executed if the lefthand side is true. Thus, if you have this code,
implication(X) :-
(X = a ->
write('Argument a received.'), nl
; X = b ->
write('Argument b received.'), nl
;
write('Received unknown argument.'), nl
).
Then it will write different things depending on it argument:
?- implication(a).
Argument a received.
true.
?- implication(b).
Argument b received.
true.
?- implication(c).
Received unknown argument.
true.
(link to documentation.)
It's a local version of the cut, see for example the section on control predicated in the SWI manual.
It is mostly used to implement if-then-else by (condition -> true-branch ; false-branch). Once the condition succeeds there is no backtracking from the true branch back into the condition or into the false branch, but backtracking out of the if-then-else is still possible:
?- member(X,[1,2,3]), (X=1 -> Y=a ; X=2 -> Y=b ; Y=c).
X = 1,
Y = a ;
X = 2,
Y = b ;
X = 3,
Y = c.
?- member(X,[1,2,3]), (X=1, !, Y=a ; X=2 -> Y=b ; Y=c).
X = 1,
Y = a.
Therefore it is called a local cut.
It is possible to avoid using it by writing something more wordy. If I rewrite Stephan's predicate:
implication(X) :-
(
X = a,
write('Argument a received.'), nl
;
X = b,
write('Argument b received.'), nl
;
X \= a,
X \= b,
write('Received unknown argument.'), nl
).
(Yeah I don't think there is any problem with using it, but my boss was paranoid about it for some reason, so we always used the above approach.)
With either version, you need to be careful that you are covering all cases you intend to cover, especially if you have many branches.
ETA: I am not sure if this is completely equivalent to Stephan's, because of backtracking if you have implication(X). But I don't have a Prolog interpreter right now to check.