Flatten list of negative numbers - list

I am trying to flatten the following type of Tcl lists:
-1587.500000 {} 1587.500000
or
15.78 18.56 {} {} {} {} 15.6
So I try:
[struct::list flatten -full $lineToFlatten]
But when lineToFlatten starts with the negative number the following type of error message is issued (for example):
Unknown option "-1587.500000 {} 1587.500000", should be either -full, or --
How to resolve this?

Normally, the correct way is to use the -- to denote the end of the options. But there is a bug that prevents you from doing that (missing lrange).
The correct way to do that is:
struct::list flatten -full -- {-1587.500000 {} 1587.500000}
But this does not work because struct has a bug.
If you want to fix it, open the package file for struct::list, you can get the filename with
package ifneeded struct::list [package require struct::list]
Then edit the proc ::struct::list::Lflatten.
Change the line with
-- {break}
to
-- {set args [::lrange $args 1 end];break}
Anyway, I suggest filling a bug record.

I just discovered how to use this function ^^
Okay, I can't say why it acts like this, but it throws me an error for anything like:
[struct::list flatten -full $lineToFlatten]
[struct::list flatten -full {-1587.500000 {} 1587.500000}]
It seems that it interprets the negative sign as a switch/flag instead of an element of the list. However, it works if I do:
[struct::list flatten -full {{-1587.500000} {} 1587.500000}]
[struct::list flatten -full [list $lineToFlatten]]
The first one isn't very practical, since you'll have a long command and you have to put the braces manually for the first negative number. I found the second workaround while testing a bit around.
I hope it helps :)

Related

Converting list of clauses to a query?

let say i have the following facts :
book(65).
own(named('Peter'), 65).
now got the query as a list of clauses :
[what(A), own(named('Peter'), A)]
or
[who(X), book(A), own(X, A)] .
how do I make a rule that accept this list and return the result. Keep in mind that the question could be Why,When,Who...
I went the usual way :
query_lst([]).
%% query_lst([what(Q)|T], Q) :- query_lst(T).
query_lst([H|T]) :- write('?- '),writeln(H),
call(H), query_lst(T).
but this does not allow binding of Q in wh(Q) to the answer which could be in any of the facts that are called by call()
Additional complication I did not forsee is that the query :
(what(A), own(named('Peter'), A).
would fail, because there is no what(X), fact in the DB.
I have to just bind somehow the variable A /that is in what()/ to query_lst(Goals,A) and of course remove what(X) from the list /which i can do with select/3 /
any idea how to bind list-Wh-var to query_lst result ?
my current solution (assumes Q is first element):
query_lst([G|Gs],Res) :- G =.. [Q,Res], member(Q,[what,why,who,when]), lst2conj(Gs,Conj), call(Conj).
Simply convert the list of goals into a conjunction and call it:
list_to_conjunction([], true).
list_to_conjunction([Goal| Goals], Conjunction) :-
list_to_conjunction(Goals, Goal, Conjunction).
list_to_conjunction([], Conjunction, Conjunction).
list_to_conjunction([Next| Goals], Goal, (Goal,Conjunction)) :-
list_to_conjunction(Goals, Next, Conjunction).
Then:
query_list(Goals) :-
list_to_conjunction(Goals, Conjunction),
call(Conjunction).
You got an answer, but it was an answer to your question, not to what you really wanted. Also, you edited your question after you accepted that answer, which isn't very helpful. Typically it's better to open a new question when you have... a new question.
Here is an answer to what you seem to want, which is not exactly what you asked. You have lists of the form [WhPart | Rest] where the WhPart is a wh-word with a variable, and the Rest is a list of goals. You want to execute these goals and get the variable in the wh-term bound.
The good news is that, since the variable in the wh-word also occurs in the goals, it will be bound if you execute them. No extra work is needed. Executing the goals is enough. If the wh-part is really at the start of the list, you can do the whole thing like this:
query([_WhPart | Body]) :-
call_body(Body).
call_body([]).
call_body([Goal | Goals]) :-
call(Goal),
call_body(Goals).
For example:
?- query([who(X), book(A), own(X, A)]).
X = named('Peter'),
A = 65.
?- query([what(A), own(named('Peter'), A)]).
A = 65.
As you can see, there is no need to convert the query to a conjunctive goal: Executing the queries in sequence is exactly the same as executing their conjunction.
Also, it doesn't actually matter which wh-word is used; the only thing that really matters is the variable contained within the term. For this reason the above version does no checking at all, and the _WhPart could be anything. If you want to check that it is a valid term, you can do the following:
query([WhPart | Body]) :-
wh(WhPart),
call_body(Body).
wh(who(_X)).
wh(what(_X)).
wh(when(_X)).
This buys you some "type checking":
?- query([foo(A), own(named('Peter'), A)]).
false.
But not a lot, since you don't know if the wh-word actually fits what is being asked:
?- query([when(A), own(named('Peter'), A)]).
A = 65.

Two action after then in Ocaml

Is it possible to make two actions after a then in Ocaml ?
I try to search and I found that I could use a semicolon.
Should I use it like this ? :
let test (a:int)=
if a = 0
then print_int(1);print_int(2)
else()
;;
It's just an example. In my case I want to launch a function and give a tuple like that :
let move_square(x,y:int*int):int*int=
..
let direction : int = Random.int(5);
if direction = 0
then draw_square(x,y+1);x,y+1
else ..
Thanks for helping me
You can refer to §Séquence of https://caml.inria.fr/pub/old_caml_site/FAQ/qrg-fra.html.
Generally you have to group ocaml statement in an if-then-else structure,
either by using explicitly beginand end keywords, or by using parenthesis to group your sequence.

Printing Values from a list without spaces in python 2.7

Suppose I have a list like
list1 = ['A','B','1','2']
When i print it out I want the output as
AB12
And not
A B 1 2
So far I have tried
(a)print list1,
(b)for i in list1:
print i,
(c)for i in list1:
print "%s", %i
But none seem to work.
Can anyone suggest an alternate method
Thank you.
From your comments on #jftuga answer, I guess that the input you provided is not the one you're testing with. You have mixed contents in your list.
My answer will fix it for you:
lst = ['A','B',1,2]
print("".join([str(x) for x in lst]))
or
print("".join(map(str,lst)))
I'm not just joining the items since not all of them are strings, but I'm converting them to strings first, all in a nice generator comprehension which causes no memory overhead.
Works for lists with only strings in them too of course (there's no overhead to convert to str if already a str, even if I believed otherwise on my first version of that answer: Should I avoid converting to a string if a value is already a string?)
Try this:
a = "".join(list1)
print(a)
This will give you: AB12
Also, since list is a built-in Python class, do not use it as a variable name.

How to avoid backslashitis?

I have the following code:
proc list_backslash {} {
array unset options
array set options {
-inputs {vdd}
-outputs {vss}
}
set inputs { vdd2 vdd dvdd }
set outputs { vss2 vss dvss }
set updateOptions [ list \
-inputs $inputs \
-outputs $outputs ]
array set options $updateOptions
foreach {k v} [array get options] {
puts "$k => $v"
}
}
Since I have a lot of key-value pairs in updateOptions, there is a severe backslashitis! Is there a better way to do code updateOptions? I tried subst + braces {} and realized it does not preserve the list structure thus dooming it.
Generally speaking, if you need to continue a line you have to use a quoting mechanism of some kind with Tcl. Otherwise, the command call ends when the line ends. The [brackets] can include multiple statements too; it's legal, but really not recommended.
But that does mean that sometimes you've got awkward alternatives. Perhaps you'll be best off with doing this:
set updateOptions {
-inputs $inputs
-outputs $outputs
}
foreach {key value} $updateOptions {
set options($key) [subst $value]
}
The array set command isn't especially efficient until you get to huge numbers of options (many thousands) when the code is inside a procedure.
Or if you've got Tcl 8.6, dict map is perhaps better:
array set options [dict map {key value} $updateOptions {subst $value}]
Be aware that subst is not a particularly efficient command in Tcl 8.6 except when used with a literal argument. That's because with variable arguments, it compiles them to bytecode at runtime.
option a) Put it all on one line.
option b) Structure the code as:
set options(-inputs) $inputs
set options(-outputs) $outputs
option c) Learn to like backslashes.

Prolog - sending a list as a parameter to be displayed

I'm trying to write a program to find a route between towns, add the path to the list and then, ad the end display it.
I think adding to the list works, but I'm having the problem displaying the list, don't know how can I pass a list as a parameter to be used when it's done finding the path? Hope you guys can help. Here's the code:
connected(middlesbrough, stockton).
connected(middlesbrough, darlington).
connected(stockton, sunderland).
connected(darlington, thirsk).
connected(stockton, newcastle).
connected(newcastle, york).
connected(thirsk, york).
connected(york, leeds).
connected(leeds, huddersfield).
connected(leeds, dewsbury).
connected(huddersfield, manchester).
connected(dewsbury, manchester).
run(List):-
write('Enter Starting City :'),
read(Start),
write('Enter Finishing City :'),
read(End),
findroute(Start,End),
writeList([List]).
findroute(Start,End):-
connected(Start,End).
findroute(Start,End):-
add(Start, List, [Start | List]),
connected(Start,Link), findroute(Link,End).
add(A,B,[A|B]).
writeList([]).
writeList([Head | Tail]):-
write(Head),
nl,
writeList(Tail).
Your findroute/2 predicate does not return the list, so the output can't work.
The call should look something like this:findroute(Start,End,List)
Obviously, the findroute/2 predicate must be changed to findroute/3:
findroute(Start,End,[Start,End]):-
connected(Start,End).
findroute(Start,End,List):-
connected(Start,Link),
add(Start,Rest,List),
findroute(Link,End,Rest).
(hint: be sure you understand why the add/3 call works even though Rest is uninstantiated at that point. Otherwise your tutor won't believe that this code is your homework! ;-) )
You may want to add a cut at the end of the first clause if you only want to find the shortest route.
Finally, List is already a list, so don't put square brackets around it when calling writeList/1!