ASP Clingo - getting the exact count of atoms - aggregate

I'm looking forward to assign a specific count of persons to a specific shift. For example I got six persons and three different shifts. Now I have to assign exact two persons to every shift. I tried something like this but..
NOTE: this won't work, so please edit as fast as possible to misslead people, I even removed the "." after it so nobody is copying it:
person(a)
person(b)
person(c)
person(d)
person(e)
person(f)
shift("mor")
shift("aft")
shift("nig")
shiftCount(2).
{ assign(P,S) : shift(S)} = 1 :- person(P).
% DO NOT COPY THIS! SEE RIGHT ANSWER DOWN BELOW
:- #count{P : assign(P,"mor")} = K, shiftCount(K).
:- #count{P : assign(P,"aft")} = K, shiftCount(K).
:- #count{P : assign(P,"nig")} = K, shiftCount(K).
#show assign/2.
Is this possible to count the number of assigned shifts, so I can assign exactly as many people as a given number?
The output of the code above (when the "." are inserted) is:
clingo version 5.5.0
Reading from stdin
Solving...
Answer: 1
assign(a,"nig") assign(b,"aft") assign(c,"mor") assign(d,"mor")
assign(e,"mor") assign(f,"mor")
SATISFIABLE
Models : 1+
Calls : 1
Time : 0.021s (Solving: 0.00s 1st Model: 0.00s Unsat: 0.00s)
CPU Time : 0.000s
Here you can defently see, that the morning ("mor") shift is used more than two times, as difined in the shiftCount. What do I need to change to get the wanted result?

Replace your 3 lines constraints with
{assign(P,S): person(P)} == K :- shift(S), shiftCount(K).
or alternatively if you want to use the constraint writing:
:- {assign(P,S): person(P)} != K, shift(S), shiftCount(K).
First line states: For a given shiftCount K and for every shift S: the number of assignments over all people P for this shift S is K.
The constraint reads: it can not be the case for a shiftCount K and a shift S that the number of assignments over all people P to the shift S is not K.
Please do not alter your question / sample code dramatically since this may leads to the case that this answer won't work anymore.

Related

Clingo/ASP: Best way to generate characters in a story generator

I am trying to write a story generator in Clingo.
I am trying to say "new characters can be born if existing characters give birth to them." I define new characters as entity(<int\>), which is the best way I could think of to representing entities. I cannot hardcode this as varying number of entities can be created in a story.
My code is :
% Create instances of time, only 3 for testing
time(0..2).
% Arrow of time flows forward
next_t(T, T+1) :- time(T), time(T+1).
% Entity 1 exists at time 0.
entity(1, 0).
% If an entity ever existed, that ID is taken and cannot be assigned to
% other entities
entity_id(ID) :- entity(ID, _).
% If an entity exists, he can give birth to a new entity
% The ID of the new entity will be 1 more than ID of all current entities.
birth(X, Y, T) :- entity(Y, T), X = #max{X1+1:entity_id(X1)}, time(T).
% At each time instant, only 1 entity can be born, as only 1 event can happen per time instant.
% This also should prevent infinite entities to be created.
:- birth(X1, _, T), birth(Y1, _, T), X1!=Y1.
% In case of a birth, create a new entiti the next time instant.
entity(X, T1) :- birth(X, _, T), next(T, T1).
#show entity_id/1.
#show entity/2.
#show birth/3 .
However, output is :
entity_id(1) entity(1,0) birth(2,1,0)
entity(2, 1) is never created, nor are entity(3, 2) or entity(4, 3).
What am I doing wrong? Is there a better way to do this?
You seem to be thinking that ASP statements happen in order from first to last or something like that.
But in fact they're just rules about a collection of atoms. The rules always hold. In particular, the rule:
entity_id(ID) :- entity(ID, _).
says nothing about duplicates. It just says that for every entity which has an ID ID, ID is an entity_id.
If you want to encode the rule that each ID is used once, you should write it as:
:- {entity(ID,_)} > 1; entity_id(ID).
Also you try to construct "ID's" which are "one more than all current entities", but there's no such thing as "current" entities. All we have to guide us are the time-steps.
Let's try writing this in a way that keeps our timesteps explicit throughout.
% Create instances of time, only 3 for testing
time(0..2).
% Entity eve exists at time 0.
entity(1, 0).
nextID(2, 0).
% If an entity existed at the previous time-step, they continue to exist
% at the next time-step (as I understand, no entity dies).
entity(ID, T) :- entity(ID, T-1); time(T).
% Any entity who was alive on the previous time-step can give birth to
% a child at time T. This child's ID is the current `nextID`
% Note this is a _choice_ rule. The entity _can_ give birth, they don't
% have to. Also we only allow at most one of these births to happen at
% each time-step.
{birth(ChildID, ParentID, T) : entity(ParentID,T-1)} <= 1 :- nextID(ChildID,T).
% Once born, an ID becomes an entity.
entity(ID,T) :- birth(ID,_,T).
% If an entity was born at the previous time-step, the nextID increases by one
% for this time-step.
nextID(ID+1,T) :- nextID(ID,T-1); time(T); entity(ID,T-1).
% Otherwise it stays the same.
nextID(ID,T) :- nextID(ID,T-1); time(T); not entity(ID,T-1).
#show birth/3.
Running this I find there are 5 models.
$ clingo entities.asp 0
clingo version 5.3.1
Reading from entities.asp
Solving...
Answer: 1
% ^ Nobody is ever born
Answer: 2
birth(2,1,2)
% ^ Nobody born at time 1. 1 births a child at time 2
Answer: 3
birth(2,1,1) birth(3,2,2)
% ^ 1 births a child at time 1 and that child gives birth at time 2.
Answer: 4
birth(2,1,1)
% ^ 1 births a child at time 1. Nobody is born at time 2.
Answer: 5
birth(2,1,1) birth(3,1,2)
% ^ 1 births two children; one at time 1 and another at time 2.
SATISFIABLE
Models : 5
Calls : 1
Time : 0.011s (Solving: 0.00s 1st Model: 0.00s Unsat: 0.00s)
CPU Time : 0.004s

create subset and use each atom only once

I am totally new in asp. I need to create a group of teams. Each group must consist of 3 randomly chosen teams. A team can be in only one group.
Thanks in advance. Here is my code
team(fener;galata;besik;van;adana;mardin).
neq(X,Y) :- X!=Y,team(X),team(Y).
count(C) :- C = #count{ T : team(T)}.
C/3 {group(X,Y,Z):team(X),team(Y),team(Z), neq(X,Y),neq(X,Z),neq(Z,Y) } C/3 :- count(C).
#show group/3.
a possible output could be
group(fener;besik;van) group(galata;mardin;adana)
The output you want is not possible:
group(a;b;c).
implies:
group(a). group(b). group(c).
A possible output would be:
group(a,b,c).
But ASP is not really friendly with variable arguments atoms, or list elements as parameters. A simpler output to manage would be:
group(1,a). group(1,b). group(1,c).
And this is very easy to generate, and allows us to avoid the costly #count:
% Data
#const nb_group=2.
group(1..nb_group).
team(fener;galata;besik;van;adana;mardin).
% Assign 3 teams to each group
3{ group(G,T): team(T) }3 :- group(G).
% Two (almost) equilavent constraints:
1{ group(G,T): group(G) }1:- team(T). % a team is in only one group
OR
:- team(T) ; not group(_,T). % a team has no group
I think, have found the solution.
team(fener;galata;besik;van;adana;mardin).
neq(X,Y) :- X!=Y,team(X),team(Y).
count(C) :- C = #count{ T : team(T)}.
C/3 {group(X,Y,Z):team(X),team(Y),team(Z), neq(X,Y),neq(X,Z),neq(Z,Y) } C/3 :- count(C).
exist_in_group(T) :- group(T,_,_).
exist_in_group(T) :- group(_,T,_).
exist_in_group(T) :- group(_,_,T).
:- team(T), not exist_in_group(T).
#show group/3.
The output:
clingo version 5.0.0
Solving...
Answer: 1
group(besik,fener,adana) group(galata,mardin,van)
SATISFIABLE
Models : 1+
Calls : 1
Time : 0.011s (Solving: 0.00s 1st Model: 0.00s Unsat: 0.00s)
CPU Time : 0.000s

triple sum in matlab

I want to compute the following sum :
I have tried using the following code :
I = imread('C:\Users\Billal\Desktop\image.png');
[x,y,z]=size(I);
x=(1:x) ;
y=(1:y) ;
z=(1:z) ;
Fx=ones(size(x));
Fy=ones(size(y));
Fz=ones(size(z));
X=x*Fy';
Y=Fx*y';
Z=z*Fz';
f=I(X,Y,Z);
sum1 = sum(f(:));
[x1,y1,z1]=size(I);
total = sum1/(x1*y1*z1);
But the result is 0 . I could not figure out where is the problem ? I am following this tutorial .
https://www.mathworks.com/matlabcentral/newsreader/view_thread/126366
Please help me to solve this question .
You can do this in a single step:
result=1/prod(size(I))* sum(I(:));
In the end, the equation just adds up values of the whole image.
The question you link to needs to sum over values of x and y. You don't, you just need to sum over indexes, thus there is no need of all those Fx,Fy things

Can someone explain the TI BASIC 🔺List command?

I understand that the command compares and can subtract values, but I don't see exactly how that works. I've used a TI BASIC programming tutorial site (http://tibasicdev.wikidot.com/movement-explanation) and I need clarification on 🔺List as a whole.
This portion of the code with 🔺List is as follows,:
:min(8,max(1,A+sum(ΔList(Ans={25,34→A
:min(16,max(1,B+sum(ΔList(K={24,26→B
and the website explains the code like this.:
"This is how this code works. When you press a key, its value is stored to K. We check to see if K equals one of the keys we pressed by comparing it to the lists {24,26 and {25,34. This results in a list {0,1}, {1,0}, or {0,0}. We then take the fancy command Δlist( to see whether to move up, down, left or right. What Δlist( does is quite simple. Δlist( subtracts the first element from the second in the previous list, and stores that as a new one element list, {1}, {-1}, or {0}. We then turn the list into a real number by taking the sum of the one byte list. This 1, -1, or 0 is added to A."
The ΔList( command subtracts every element in a list from its previous element. This code uses some trickery with it to compactly return 1 if a key is pressed and -1
ΔList( calculates the differences between consecutive terms of a list, and returns them in a new list.
ΔList({0,1,4,9,16,25,36})
{1 3 5 7 9 11}
That is, ΔList({0,1,4,9,16,25,36}) = {1-0, 4-1, 9-4, 16-9, 25-16, 36-25} = {1 3 5 7 9 11}.
When there are only two elements in a list, ΔList({a,b}) is therefore equal to {b-a}. Then sum(ΔList({a,b})) is equal to b-a, since that's the only term in the list. Let's say that K is 26 in your example; that is, the > key is pressed.
B+sum(ΔList(K={24,26→B Result of expression:
K 26
K={24,26 {0,1}
ΔList(K={24,26 {1} = {0 - 1}
sum(ΔList(K={24,26 -1
B [current x-position of player]
B+sum(ΔList(K={24,26→B [add 1 to current x-pos. of player]
Similarly, B will be decreased if key 24, the left key, is pressed.

partial Distance Based RDA - Centroids vanished from Plot

I am trying to fir a partial db-RDA with field.ID to correct for the repeated measurements character of the samples. However including Condition(field.ID) leads to Disappearance of the centroids of the main factor of interest from the plot (left plot below).
The Design: 12 fields have been sampled for species data in two consecutive years, repeatedly. Additionally every year 3 samples from reference fields have been sampled. These three fields have been changed in the second year, due to unavailability of the former fields.
Additionally some environmental variables have been sampled (Nitrogen, Soil moisture, Temperature). Every field has an identifier (field.ID).
Using field.ID as Condition seem to erroneously remove the F1 factor. However using Sampling campaign (SC) as Condition does not. Is the latter the rigth way to correct for repeated measurments in partial db-RDA??
set.seed(1234)
df.exp <- data.frame(field.ID = factor(c(1:12,13,14,15,1:12,16,17,18)),
SC = factor(rep(c(1,2), each=15)),
F1 = factor(rep(rep(c("A","B","C","D","E"),each=3),2)),
Nitrogen = rnorm(30,mean=0.16, sd=0.07),
Temp = rnorm(30,mean=13.5, sd=3.9),
Moist = rnorm(30,mean=19.4, sd=5.8))
df.rsp <- data.frame(Spec1 = rpois(30, 5),
Spec2 = rpois(30,1),
Spec3 = rpois(30,4.5),
Spec4 = rpois(30,3),
Spec5 = rpois(30,7),
Spec6 = rpois(30,7),
Spec7 = rpois(30,5))
data=cbind(df.exp, df.rsp)
dbRDA <- capscale(df.rsp ~ F1 + Nitrogen + Temp + Moist + Condition(SC), df.exp); ordiplot(dbRDA)
dbRDA <- capscale(df.rsp ~ F1 + Nitrogen + Temp + Moist + Condition(field.ID), df.exp); ordiplot(dbRDA)
You partial out variation due to ID and then you try to explain variable aliased to this ID, but it was already partialled out. The key line in the printed output was this:
Some constraints were aliased because they were collinear (redundant)
And indeed, when you ask for details, you get
> alias(dbRDA, names=TRUE)
[1] "F1B" "F1C" "F1D" "F1E"
The F1? variables were constant within ID which already was partialled out, and nothing was left to explain.