Re: Solving inequation
- To: mathgroup at smc.vnet.net
- Subject: [mg2099] Re: Solving inequation
- From: Bernd.Cebulski at e-technik.tu-chemnitz.de (Bernd Cebulski)
- Date: Fri, 29 Sep 1995 01:15:45 -0400
- Organization: TU Chemnitz
In article <DFCG6A.Lz6 at wri.com> uthaisom at veena.cps.msu.edu (Patchrawat Ut= haisombut) writes: >From: uthaisom at veena.cps.msu.edu (Patchrawat Uthaisombut) >Subject: Solving inequation >Date: Sat, 23 Sep 1995 05:49:21 GMT >Hi, >I am a new Mathematica user. >I wonder if Mathematica can solve inequation. >Something like > Solve[ k+s < s+1, k] >If there is no such build-in function, >suggestion to implement this is also appreciated. -------------------------------------------------------------- = There is no solution for such problems built in. There were several discu= ssions before about this topic. Here are a few solutions for your task. If you g= et = other interesting answers per e-mail please forward them to me. = =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D forwarded messages follow =3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D <from ronald at sccs.chukyo-u.ac.jp> In any case, I went ahead and asked WRI tech support. = It seems that there was nothing built in after al. But, the tech support rep, Ed Greaves, volunteered to write a function to do the job. As I suspecte, his version is much better than what I would have written. Here it is: convertIneq[ x_[lhs_,rhs_] ] :=3D Module[{temp, const, result}, temp =3D Expand[lhs - rhs]; (* move all terms to LHS *) const =3D If[Head[temp] =3D=3D=3D Plus, (* >1 term?*) Select[temp,NumberQ], 0]; result =3D x[temp - const, -const ]; (* The next is needed only if you wish = the rhs to always be non-negative *) If[const>0, (* is rhs negative? *) result =3D Map[Minus, result]; result =3D result /. { LessEqual->GreaterEqual GreaterEqual->LessEqual } ]; (* Note: The 'If' has only a 'Then' clause *) result ] Everything that I send out, I have to type in by hand. Once the screen scrolls, I cannot return to check or edit. So, there may be a type or two above. But, I do not think anything serious. The function itself is a forehead slapper: As soon as I saw it, I slapped my forehead and thought "Why didn't I write this?" Of course, I never would have written anything remotely as neat and clean as this. To repeat, the above is a very slight modification of a = function written by Edmumd Greaves of WRI. I have tried it. Ed has thought of and covered cases I = would not have. It seems to work well. Hope this is of help Ron Notestine. -------------------------------------------------------------------------= ------ <from rubin at msu.edu> Yes, but the only way I know how to do it is like pulling teeth. (Questi= ons about inequalities come up on this list periodically, but I haven't seen a killer answer yet.) I can get an answer to this using two massive klud= ges: inserting slacks/surpluses to convert and from equations, and defining an= "inverse" for the absolute value function. (Yeah, I know, it's not invertible, but humor me. :-) ) = First, I'll define a bunch of substitution rules (I'm being a little more= general than this specific example): = In[1]:=3D ineq2eq :=3D {(a_) <=3D (b_) -> a + slack =3D=3D b, (a_) < (b_) -> a + strongslack =3D=3D b, (a_) >=3D (b_) -> a - surplus =3D=3D b, (a_) > (b_) -> a - strongsurplus =3D=3D b}; In[2]:=3D eq2ineq :=3D {(a_) =3D=3D slack + (b_) -> a >=3D b, (a_) =3D=3D -slack + (b_) -> a <=3D b, (a_) =3D=3D strongslack + (b_) -> a > b, (a_) =3D=3D -strongslack + (b_) -> a < b, (a_) =3D=3D surplus + (b_) -> a >=3D b, (a_) =3D=3D -surplus + (b_) -> a <=3D b, (a_) =3D=3D strongsurplus + (b_) -> a > b, (a_) =3D=3D -strongsurplus + (b_) -> a < b}; In[3]:=3D sreduce :=3D {slack _?Positive -> slack, slack _?Negative -> -slack, surplus _?Positive -> surplus, surplus _?Negative -> -surplus, strongslack _?Positive -> strongslack, strongslack _?Negative -> -strongslack, strongsurplus _?Positive -> strongsurplus, strongsurplus _?Negative -> -strongsurplus}; In[4]:=3D invabs :=3D {(a_) =3D=3D (b_.) + (c_.) InverseFunction[ Abs, 1, 1][d_] -> a =3D=3D b + c d || a =3D=3D b - c d}; = The symbols "slack," "strongslack," "surplus" and "strongsurplus" should probably be protected, to keep you from accidentally assigning them value= s = (they're really placeholders). The "invabs" pattern replaces any call to= the (nonexistent) inverse of the absolute value function with a disjuncti= on of plus and minus the argument to the "inverse." (In other words, when M= ma sees y =3D=3D Abs[ x ], it solves for x by setting x to the inverse of th= e Abs function at y, which is really x =3D=3D y || x =3D=3D -y.) Now comes the= fun: = In[5]:=3D prob :=3D 1 > Abs[ u - 2 ]; (* original problem *) In[6]:=3D prob =3D prob /. ineq2eq (* convert to equations *) Out[6]=3D {1 - strongsurplus =3D=3D Abs[-2 + u]} In[7]:=3D prob =3D Reduce[ prob, u ] (* solve for u *) Out[7]=3D (-1) u =3D=3D 2 + Abs [1 - strongsurplus] (* note "inverse" abs funct= ion *) In[8]:=3D prob =3D prob /. invabs (* get rid of "inverse function" *) Out[8]=3D u =3D=3D 3 - strongsurplus || u =3D=3D 1 + strongsurplus In[9]:=3D prob =3D prob /. sreduce (* eliminate multipliers of surplus; not needed in this particular example = *) Out[9]=3D u =3D=3D 3 - strongsurplus || u =3D=3D 1 + strongsurplus In[10]:=3D prob =3D prob /. eq2ineq (* back to inequalities *) Out[10]=3D u < 3 || u > 1 = > Help with this simple example will lead me to using it for more complex= = > inequalities.. = Well, maybe. It gets a lot messier with multiple variables, and it relie= s heavily on Reduce being able to do something with the equation in the fir= st place. I tried something like Abs[ x - 3 ] < Abs[ 2 - 2 x ] (or somethin= g along those lines) and Reduce quit in disgust. -------------------------------------------------------------------------= -- <from g.gsaller at amda.or.at> There was a module called ConvertIneq in the mathgroup conference. I dont= know the author. This module converted inequalities to standard form for linear programmin= g. I changed this module to SolveIneq to solve simple inequalities. solveIneq[ x_[lhs_, rhs_] ] :=3D Module[{temp, const, fact, result}, temp =3D Expand[lhs - rhs]; const =3D If[Head[temp] =3D=3D=3D Plus, Select[temp, NumberQ], 0]; fact =3D If[Head[temp] =3D=3D=3D Times, Select[temp, NumberQ], If[Head[temp[[2]]] =3D=3D=3D Times, Select[temp[[2]], NumberQ]],1]; result =3D x[(temp - const)/fact, -const/fact]; If[fact < 0, result =3D result /. {Less -> Greater, LessEqual -> GreaterEqual, Greater -> Less, GreaterEqual -> LessEqual}]; result ] Sample Input: solveIneq[2(x-1)<(10x+5)/7+38] Guenther R. Gsaller =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D end of forwarde= d messages =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D = PS: There is some hope that WR will implement facilities for solving = inequalities in the next release of MMa (perhaps 3.0?). BTW, other packages (for example DERIVE) can solve inequalities ... Hope that helps a bit, cheerio, = Bernd. =2E.-----------------------------------------------. | Chemnitz, University of Technology | |--- bernd.cebulski at e-technik.tu-chemnitz.de ---| | Phone: +49 (371) 5313318 | | Fax: +49 (371) 5313361 | | DL 1 DTP | `-----------------------------------------------=B4 =