I am trying to design a state machine which will traverse all possible transitions between states. However, the state machine cannot move from a given state back to itself. From the diagram below, I have worked out that given the number of states (N), the number of transitions is equal to N^2 - N.
Any ideas on how to approach this please?
After having misunderstood the problem the first time, here is another attempt.
So we want to transverse the graph in one go, and we are not allowed to use the same transition twice. The trick is probably to leave a track free to get back to the starting state.
states = 4 # Select number of states
path = [0] # Start in state 0 (must be zero)
def walk(path):
home_state = path[-1]
for i in range(home_state + 2, states):
# We leave a state out that we go to next
path.append(i)
path.append(home_state)
if home_state + 1 < states:
path.append(home_state + 1)
walk(path)
path.append(home_state)
walk(path)
print path
should give
[0, 2, 0, 3, 0, 1, 3, 1, 2, 3, 2, 1, 0]
Related
I would like to constrain locations to be served by the same vehicle.
I used capacity-constraints for achieving this. Say we have l = [[1,2], [3,4]] which means that location 1, 2 must be served by the same vehicle and 3, 4 as well. So 1, 2 ends up on route_1 and 3, 4 on route_2
My code for achieving this is:
for idx, route_constraint in enumerate(l):
vehicle_capacities = [0] * NUM_VEHICLES
vehicle_capacities[idx] = len(route_constraint)
route_dimension_name = 'Same_Route_' + str(idx)
def callback(from_index):
from_node = manager.IndexToNode(from_index)
return 1 if from_node in route_constraint else 0
same_routes_callback_index = routing.RegisterUnaryTransitCallback(callback)
routing.AddDimensionWithVehicleCapacity(
same_routes_callback_index,
0, # null capacity slack
vehicle_capacities, # vehicle maximum capacities
True, # start cumul to zero
route_dimension_name)
The idea is that 1,2 have a capacity demand of each 1 unit (all others have zero). As only vehicle 1 has a capacity of 2 it is the only one able to serve 1,2.
This seems to work fine if len(l) == 1. If greater the solver is not able to find a solution if though I put into l pairs of locations which were on the same route without the above code (hence without the above capacity constraints.
Is there a more elegant way to model my requirement?
Why does the solver fail to find a solution?
I have also considered the possibility of dropping visits (at a high cost) to give the solver the possibility to start from a solution which drops visits such that it will find his way fro this point to a solution without any drops. I had no luck.
Thanks in advance.
Each stop has a vehicle var whose values determine what vehicle is allowed to visit the stop. If you want to have stops 1 and 2 serviced by vehicle 0 use a member constraint on the vehicle var of each stop and set it to [0]. Since you might have other constraints that make stops optional add the value -1 to the list. It is a special value that indicates that the stop is not serviced by a vehicle.
In Python:
n2x = index_manager.NodeToIndex
cpsolver = routing_model.solver()
for stop in [1,2]:
vehicle_var = routing_model.VehicleVar(n2x(stop))
values = [-1, 0]
cpsolver.Add(cpsolver.MemberCt(vehicle_var, values))
I have used Python for a long time but I don't know how objects and the memory really work.
Until a few days ago, I thought that alpha = gamma made a variable whose name was alpha and saved in it a copy of gamma, without linking the variables to each other. However, I have recently noticed that that doesn't happen. Both variables actually point to the same object. Nevertheless, the variables become independent when you change the data in one of them (depending on the variables).
There are many other cases in which variables don't behave like you would expect. This is an example I came upon:
>>> grid1=[[0]*4]*4
>>> grid2=[[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0]]
>>> grid1 == grid2
True
>>> grid1[2][3]+=1
>>> grid2[2][3]+=1
>>> grid1
[[0, 0, 0, 1], [0, 0, 0, 1], [0, 0, 0, 1], [0, 0, 0, 1]]
>>> grid2
[[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 1], [0, 0, 0, 0]]
I have tried to find more information about how = and other commands treat variables and found some threads, but I have many questions whose answer I don't know yet:
Why did the behavior shown above with the lists take place?
What should be done in order to avoid it (make grid1 behave like grid2)?
Does this have anything to do with the modifiability of the variables? What does it really mean for a variable to be modifiable?
When are variables the same object or different ones? How do you know if a command creates a separate variable or not (x+=y vs x = x + y, append vs +)?
Is there an == which would have returned false in the example above (is wouldn't work, those two variables were created in different steps and independently so they won't be in the same place in the memory) because in grid1 all lists were in the same place in the memory while in grid2 they were independent?
I haven't been able to find the answers to those questions anywhere, could anyone give a brief answer to the questions or provide a reference which explained these concepts? Thanks.
Why did the behavior shown above with the lists take place?
Because lists and other mutable collections do not create a new object when you set them to a variable.
What should be done in order to avoid it (make grid1 behave like grid2)?
grid1=[[[0] for _ in range(4)] for _ in range(4)] would make it work as you want. This is because it actually creates a new list each time instead of duplicating it (like [[0]*4]*4 does).
Does this have anything to do with the modifiability of the variables? What does it really mean for a variable to be modifiable?
Collections such as strings are immutable so when you do a = "hi";b = a; b += "!" b is set to a new string that copies a and then to a new string that copies b and adds "!".
Lists instead operate on the same object so when you do a = [];b = a;b.append(1) b is set to a and then it appends 1 to b (which references a in memory).
When are variables the same object or different ones? How do you know if a command creates a separate variable or not (x+=y vs x = x + y, append vs +)?
It Depends more on the data structure rather than on the operator or method.
Mutable types: list, set, dict.
Immutable types: tuple, frozenset, string.
Is there an == which would have returned false in the example above (is wouldn't work, those two variables were created in different steps and independently so they won't be in the same place in the memory) because in grid1 all lists were in the same place in the memory while in grid2 they were independent?
== evaluates the equality of values (i.e. if they contain the same) while is evaluates if both are the same object. (Try testing == and is on two equal lists. In the first case a = [1]; b = [1] and in the second case a = [1]; b = a.
I am trying to write a program that returns the frequency of a certain pattern. My frequency list is initially a list of zeros, and I want to increase a certain zero by one depending on the pattern. I have tried the code below, but it does not work.
FrequencyArray[j] = FrequencyArray[j]+1
Is there another way to increase one element of the list by 1 without affecting the other elements?
While your approach should work, this would be the alternative:
FrequencyArray[j] += 1
Example:
>>> zeros = [0, 0, 0]
>>> zeros[1] += 1
>>> zeros
[0, 1, 0]
I'm very new to constraint programming and try to find some real situations to test it.
I found one i think may be solved with CP.
Here it is :
I have a group of kids that i have to assign to some activities.
These kids fill a form where they specify 3 choices in order of preference.
Activities have a max number of participant so, the idea is to find a solution where the choices are respected for the best without exceedind max.
So, in first approach, i defined vars for kids with [1,2,3] for domain (the link between the number of choice, activity and children being known somewhere else).
But then, i don't really know how to define relevant constraints so I have all the permutation (very long) and then, i have to give a note to each (adding the numbers of choices to get the min) and eliminate results with to big groups.
I think there must be a good way to do this using CP but i can't figure it out.
Does someone can help me ?
Thanks
I'm not sure that I understand everything in your description, for example "so I have all the permutation (very long)" and "i have to give a note to each (adding the numbers of choices to get the min)". That said, here is a simple encoding of what I think would be a model of your problem, or at least a starter.
It's written in MiniZinc and is shown below with a small example of 6 kids and 4 activities. The full model (including variants of some constraints) is here as well: http://hakank.org/minizinc/max_activity.mzn
Description of the variables:
"x" is an array of decision variables containing the selected activity for each kid. "scores" is the scores (1, 2, or 3 depending on which activity that was selected) for the selected activity, and "total_score" just sums the "scores" array.
include "globals.mzn";
int: num_kids;
array[1..num_kids, 1..3] of int: prefs;
int: num_activities;
array[1..num_activities] of int: activity_size;
% decision variables
array[1..num_kids] of var 1..num_activities: x; % the selected activity
array[1..num_kids] of var 1..num_activities: scores;
var int: total_score = sum(scores);
solve maximize total_score;
constraint
forall(k in 1..num_kids) (
% select one of the prefered activities
let {
var 1..3: p
} in
x[k] = prefs[k,p] /\
scores[k] = 4-p % score for the selected activity
)
/\ % ensure size of the activities
global_cardinality_low_up(x, [i | i in 1..num_activities], [0 | i in 1..num_activities], activity_size)
;
output [
"x : ", show(x), "\n",
"scores: ", show(scores), "\n",
"total_score: ", show(total_score), "\n",
];
%
% some small fake data
%
num_kids = 6;
num_activities = 4;
% Activity preferences for each kid
prefs = array2d(1..num_kids, 1..3,
[
1,2,3,
4,2,1,
2,1,4,
4,2,1,
3,2,4,
4,1,3
]);
% max size of activity
activity_size = [2,2,2,3];
The solution of this problem instance is:
x : [1, 4, 2, 4, 3, 4]
scores: [3, 3, 3, 3, 3, 3]
total_score: 18
This is a unique solution.
Using a slightly smaller activity_size ([2,2,2,2]) we get another optimal solution (total_score = 17), since there can be just 2 kids in activity #4 (kid #6 is here forced to take activity #1 instead)
x : [1, 4, 2, 4, 3, 1]
scores: [3, 3, 3, 3, 3, 2]
total_score: 17
There is two other possible selections for the second variant, namely
x : [1, 4, 2, 2, 3, 4]
scores: [3, 3, 3, 2, 3, 3]
total_score: 17
----------
x : [1, 2, 2, 4, 3, 4]
scores: [3, 2, 3, 3, 3, 3]
total_score: 17
Update: I also did a Picat model using the same principal approach: http://hakank.org/picat/max_activity.pi .
Update 2: The above model assumes that all kids get some of their preferred activities. When this assumption is not met one have then fix this somehow instead of just throwing a "UNSATISFIED" as an answer. One way is to select some other - not preferred - activity to kid which will yield a score of 0. This is done in this model: http://hakank.org/minizinc/max_activity2.mzn
The changes compared to the original model are small:
the domain of "scores" are 0..num_activities
we add a disjunction "/ scores[k] = 0" to the forall loop that selects the activity
Since this is a maximization problem a score of 0 will not be used unless it is necessary.
I also added a sanity check that there are enough activities for all kids:
constraint
assert(sum(activity_size) >= num_kids, "There is not activities enough for all kids.")
;
I have been playing around with libspotify and encountered something a bit odd. Are the index parameters to sp_playlistcontainer_move_playlist 0 based or 1 based? They seem to be both, or maybe neither :) Specifically if I have three playlists I notice the following results:
sp_playlistcontainer_move_playlist(handle, 0, 3, false)
succeeds and moves the playlist at index 0 (the first one in the list of playlist) to the end of the list of playlists.
sp_playlistcontainer_move_playlist(handle, 0, 1, false)
fails, returning SP_ERROR_INVALID_INDATA, which according to the API specs seems to indicate I am 'trying to move a folder into itself'. From that I guessed that the input (original) index is 0 based, and the target index is 1 based. This is odd, but this
sp_playlistcontainer_move_playlist(handle, 0, 2, false)
does appear to move the first playlist (from index 0) to the second slot in the list of playlists (at what I would call index 1, but apparently is 2 according to libspotify).
Of course this also works
sp_playlistcontainer_move_playlist(handle, 2, 0, false)
so maybe the target index is not 1 based...or maybe 0 is just special cased. Thoughts?
It's 0-based.
Move operations always take indexes in the list's state BEFORE anything is done, so...
Moving 0 to 1 will be rejected, because it's actually a no-op.
To move the first (index 0) playlist to the second position (index 1), you actually move it to index 2, since you want it to be after the playlist that's currently at index 1. Once you make the call, libSpotify will "commit" the transaction by moving index 0 to be after index 1, then moving everything down one slot to fill in the vacant gap left at index 0.