Conditional piecewise function with dynamic boundries - pyomo

This equation is part of a large model. K1 and K2 are constants, x1 and x2 are model variables:
All other piecewise functions seen previously have fixed boundaries and I have no idea how to compute boundaries during runtime.

Related

Pivoting in simplex method for solving linear programming

A common linear programming problem below
min c'x
s.t. Ax<=b
(A is m*n, m is smaller than n)
As I know, the pivoting procedure in simplex method lets extreme point jump to another extreme point until it finds the optimal solution.
Extreme point has at most m(the number of constraints) nonzero variables. Variables in extreme point can be divided into two parts, basic variables(nonzero terms) and nonbasic variables(zero terms).
In normal condition, Pivoting change one nonbasic variable to basic variable while one basic variable become nonbasic variable in each iteration.
My question is can a nonbasic variable which was basic before become basic again? If yes, is there an clear or special example that at least one variable does.

Linear Programming - Constraints

I am trying to encode this (a small part of a project) to linear programming:
For each package p we know its length (xDimp) and width (yDimp). Also, we have the length (xTruck) and width (yTruck) of the Truck. All the numbers are integers.
Due to the design of the packages, they cannot be rotated when placed in a truck.
The Truck is represented as a matrix of 2 dimensions, only with x and y coordinates. We ignore the height.
Decision variables:
– pxy[p,x,y] = package p is in the cell with upper-right coordinates (x, y)
– pbl[p,x,y] = the bottom left cell of p has upper-right coordinates (x, y)
How do I write such constraints to set pbl and pxy variables? I supouse that I should set the variable pbl to assure that the package fits in the truck and the value of pxy variable depends of the value of pbl.
Thank you,
This is a variant of the bin packing problem, a two dimensional packing of multiple rectangles of varying widths and heights in an enclosing rectangle (2BP). If they are only allowed to be rotated by 90°, we got the orthogonal orientations rectangular packing problem, and in your case we have a non-rotatable rectangular packing problem. Its computational complexity is NP-hard, but it's not unfeasible.
From your description, the problem is already discretised, restricting the possible placements to the grid, which means that the optimum of the continuous version may not be available anymore.
One approch is to calculate certain conflict graph in advance, which represents your search space and holds information about the overlap of the rectangles:
where
Every edge represents a conflict and every node represents a possible placement within your truck. Two packages p and q intersect iff
and pairwise.
Now, the packing problem on the grid is a maximum independent set problem on the conflict graph (MIS), assuming you want to maximize the number of packages on the truck. The MIS, in turn, has the following ILP formulation:
This is an integer relaxation of the MIS but still not good for the branch and bound solving method. If C is clique in G then any independent set can pick at most one node from C, therefore use the following constraint:
The resulting linear program's number of variables grows exponentially.
In order to go further, you can try a meta constraint satisfaction approach.
Firstly, use the following contraints to make sure your packages are within the truck:
Secondly, use a set of disjunctive constraints to prevent overlap:
From that point on, you can start to formulate a meta program, as descriped here
I think this should be be enough for a start :-)
You can find more information in the literature about combinatorial optimization.
Sources:
http://www.staff.uni-mainz.de/schoemer/publications/ESA03.pdf
https://kluedo.ub.uni-kl.de/frontdoor/index/index/docId/2046

Iterate over all vectors of length `L`

How can I iterate over all possible vectors of d dimensions with specified length (e.g. unit length), where delta is the step-size.
Note that delta can by quite small, such as 1e-3 for a unit vector. d is commonly in the range of [0,5] but this is not a hard restriction!.
The dumb approach would be to use a list of delta*i for i in [0,N) and generate all possible combos like in n choose n and select those which sum up to 1. But this seems to be quite inefficient and I am sure there are better approaches which I am not aware of.
The picks should be at least close to uniformly distributed over the surface.
Ok, I think I figured out what you need. Basically, if you choose
X=(X1, X2, ..., Xn)/norm(X)
where X1, X2,..., Xn are normally distributed N(0,1) (mean 0 and standard deviation 1) and norm(X) is the L2 (Euclidian) norm of X, then it is guaranteed that the vector X is uniformly distributed across the surface of the n-dimensional unit sphere.
Now, since you want to discretize, just draw each Xi from a binomial distribution (which at the limit we know it becomes a Poisson distribution, which, via the Central Limit theorem, converges to a Gaussian distribution, see http://www.roe.ac.uk/japwww/teaching/astrostats/astrostats2012_part2.pdf ), and you're done. Of course, you'll get an exponential scaling in the dimension n, but I don't think there is any other way, as the number of such vectors scale exponentially with the dimension.

What is an appropriate data structure for storing (samples of) a 2D function?

I am looking for an efficient way of computing and storing the samples of a 2D function in my C++ program.
In order to be specific, let me start with the problem in one dimension which is easy and then explain why I cannot generalize it into 2D:
The 1-D version is as follows: We compute the samples of a function z = f(x) in the following way. We read the data from the input and corresponding to each input we compute a value of x and z = g(x). Now, we have a table of (x,z = g(x)) pairs. If for any given x, there exist only one entry then we have f(x) = z. Otherwise, f(x) = z1 + z2 + ... (where z1, z2, ... are the corresponding z entries for the specific x).
The above procedure can be implemented simply using a std::multimap. Namely at the first stage we just store the results in the map (with x as the key). Finally we can iterate through the map and if two adjacent elements are close enough we just merge them by adding their corresponding values. Assuming the complexity of computing x and z = g(x) is constant we can compute N samples in O(N log N) time complexity.
Now, I would like to generalize the algorithm into two dimensions. Namely we first compute (x,y,z=g(x,y)) pairs from the input and then set f(x,y) = z1 + z2 + ... (where for any fixed (x,y) pair, z1, z2, ... are corresponding z fields of the table entries starting with (x,y)).
The previous solution cannot be generalized because of the simple reason that one cannot define an ordering on 2D plane (indeed we could use std::multimap<std::pair<double,double>,double> but then there is no meaningful comparison to see if a key x1,y1 precedes x2,y2). However, notice that there is notion of closeness on the 2D plane: given two points (x1,y1) and (x2,y2) we can precisely tell whether they should be merged in our output or not.
Well, the very naive solution is to implement a 2D linked list (sorted in each dimension separately) where there is a better notation of adjacency. But this at least is very inefficient for insertion and (beside many other difficulties) the procedure would take O(M^2) time (where M = N * N is the number of samples on the 2D plane we want to compute)
I wonder if there is a way (more precisely a data structure) who allows me to solve the problem more efficiently?
I am really sorry for being very redundant and rather vague.

Fitting data to a 3rd degree polynomial

I'm currently writing a C++ program where I have vectors of independent and dependent data that I would like to fit to a cubic function. However, I'm having trouble generating a polynomial that can fit my data.
Part of the problem is that I can't use various numerical packages, such as GSL (long story); it's possible that it might even be overkill for my case. I don't need a very generalized solution for least squares fitting. I specifically want to fit my data to a cubic function. I do have access to Sony's vector library, which supports 4x4 matrices and can calculate their inverses, among other things.
While prototyping this in Scilab, I used a function like:
function p = polyfit(x, y, n)
m = length(x);
aa = zeros(m, n+1)
aa(:,1) = ones(m,1)
for k = 2:n+1
aa(:,k) = x.^(k-1)
end
p = aa\y
endfunction
Unfortunately, this doesn't map well to my current environment. The above example needs to support a matrix of M x N+1 dimensions. In my case, that's M x 4, where M depends on how much sample data that I have. There's also the problem of left division. I would need a matrix library that supported the inverse of matrices of arbitrary dimensions.
Is there an algorithm for least squares where I can avoid having to calculate aa\y, or at least limit it to a 4x4 matrix? I suppose that I'm trying to rewrite the above algorithm into a simpler case that works for fitting to a cubic polynomial. I'm not looking for a code solution, but if someone can point me in the right direction, I'd appreciate it.
Here is the page I am working from, although that page itself doesn't address your question directly. The summary of my answer would be:
If you can't work with Nx4 matrices directly, then do those matrix
computations "manually" until you have the problem down to something that has only 4x4 or smaller matrices. In this answer I'll outline how to do the specific matrix computations you need "manually."
--
Let's suppose you have a bunch of data points (x1,y1)...(xn,yn) and you are looking for the cubic equation y = ax^3 + bx^2 + cx + d that fits those points best.
Then following the link above, you'd write this equation:
I'll write A, x, and B for those matrices. Then following my link above, you'd like to multiply by the transpose of A, which will give you the 4x4 matrix AT*A that you can invert. In equations, the following is the plan:
A * x = B .................... [what we started with]
(AT * A) * x = AT * B ..... [multiply by AT]
x = (AT * A)-1 * AT * B ... [multiply by the inverse of AT * A]
You said you are happy with inverting 4x4 matrices, so if we can code a way to get at these matrices without actually using matrix objects, we should be okay.
So, here is a method, although it might be a little bit too much like making your own matrix library for your taste. :)
Write an explicit equation for each of the 16 entries of the 4x4 matrix. The (i,j)th entry (I'm starting with (0,0)) is given by
x1i * x1j + x2i * x2j + ... + xNi * xNj.
Invert that 4x4 matrix using your matrix library. That is (AT * A)-1.
Now all we need is AT * B, which is a 4x1 matrix. The ith entry of it is given by x1i * y1 + x2i * y2 + ... + xNi * yN.
Multiply our hand-created 4x4 matrix (AT * A)-1 by our hand-created 4x1 matrix AT * B to get the 4x1 matrix of least-squares coefficients for your cubic.
Good luck!
Yes, we can limit the problem to computing with "a 4x4 matrix". The least squares fit of a cubic, even for M data points, only requires the solution of four linear equations in four unknowns. Assuming all the x-coordinates are distinct the coefficient matrix is invertible, so in principle the system can be solved by inverting the coefficient matrix. We assume that M is more than 4, as would typically be the case for least squares fits.
Here's a write-up for Maple, Fitting a cubic to data, that hides almost completely the details of what is being solved. The first-order minimum criteria (first derivatives with respect to coefficients as parameters of sum of squares error) gets us the four linear equations, often called the normal equations.
You can "assemble" these four equations in code, then apply your matrix inverse or a more sophisticated solution strategy. Obviously you need to have the data points stored in some form. One possibility is two linear arrays, one for the x-coordinates and one for the y-coordinates, both of length M the number of data points.
NB: I'm going to discuss this matrix assembly in terms of 1-based array subscripts. The polynomial coefficients are actually one application where 0-based array subscripts make things cleaner and simpler, but rewriting it in C or any other language that favors 0-based subscripts is left as an exercise for the reader.
The linear system of normal equations is most easily expressed in matrix form by referring to an Mx4 array A whose entries are powers of x-coordinate data:
A(i,j) = x-coordinate of ith data point raised to power j-1
Let A' denote the transpose of A, so that A'A is a 4x4 matrix.
If we let d be a column of length M containing the y-coordinates of data points (in the given order), then the system of normal equations is just this:
A'A u = A' d
where u = [p0,p1,p2,p3]' is the column of coefficients for the cubic polynomial with least squares fit:
P(x) = p0 + p1*x + p2*x^2 + p3*x^3
Your objections seem to center on a difficulty in storing and/or manipulating the Mx4 array A or its transpose. Therefore my answer will focus on how to assemble matrix A'A and column A'd without explicitly storing all of A at one time. In other words we will be doing the indicated matrix-matrix and matrix-vector multiplications implicitly to get a 4x4 system that you can solve:
C u = f
If you think about the entry C(i,j) being the product of the ith row of A' with the jth column of A, plus the fact that the ith row of A' is really just the transpose of the ith column of A, it should be clear that:
C(i,j) = SUM x^(i+j-2) over all data points
This is certainly one place where the exposition would be simplified by using 0-based subscripts!
It might make sense to accumulate the entries for matrix C, which depend only on the value of i+j, i.e. a so-called Hankel matrix, in a linear array of length 7 such that:
W(k) = SUM x^k over all data points
where k = 0,..,6. The 4x4 matrix C has a "striped" structure that means only these seven values appear. Looping over the list of x-coordinates of data points, you can accumulate the appropriate contributions of each power of each data point in the appropriate entry of W.
A similar strategy can be used to assemble the column f = A' d, namely to loop over the data points and accumulate the following four summations:
f(k) = SUM (x^k)*y over all data points
where k = 0,1,2,3. [Of course in the above sums the values x,y are the coordinates for a common data point.]
Caveats: This satisfies the goal of working only with a 4x4 matrix. However one typically tries to avoid the explicit formation of the matrix of coefficients for the normal equations because these matrices are often what in numerical analysis is called ill-conditioned. In particular the cases where x-coordinates are closely spaced can cause difficulty when one tries to solve the system by inverting the matrix of coefficients.
A more sophisticated approach to solving these normal equations would be the conjugate gradient method on the normal equations, which can be done with code that computes the matrix-vector products A u and A' v one entry at a time (using what we say above about entries of A).
The accuracy of the conjugate gradient method is often satisfactory because of its natural iterative approach, esp. when one can compute the required dot-products with a little extra precision.
You should never do full matrix inversion for stability reasons. Do LU decomposition and forward-back substitution. The other solutions are spot on otherwise.