Message Boards Message Boards

GROUPS:

[?] Create a list of different functions with different variables?

Posted 9 months ago
1299 Views
|
17 Replies
|
5 Total Likes
|

Suppose we have 10 markets, each has a different supply function. Suppose that each function looks like the following:

Supply1[p1,a1, b1] = a1 + p1^b1;
Supply2 [p2, a2, b2] = a2 + p2^b2;
...;

and so on.

Rather than typing in each function, is there a way to generate them in one or a few lines?

17 Replies
Posted 9 months ago

Hi Sami,

If all of the functions have the same form why are different functions needed?

supply[p_, a_, b_] := a + p^b
supply[2, 3, 4]
(* 19 *)

19 = 3 + 2^4

Posted 9 months ago

Thank you Rohit. We have 10 different prices that we need to solve for. So we need 10 functions defined simultaneously.

Posted 9 months ago

Hi Sami,

I don't really understand why you need different functions if they all have the same definition. Anyway, here is a way to do that.

ToExpression@
    StringTemplate[
      "supply`i`[p`i`_, a`i`_, b`i`_] := a`i` + p`i`^b`i`"][<|"i" -> #|>] & /@ Range[10];

Definition@supply1
(* supply1[p1_, a1_, b1_] := a1 + p1^b1 *)
Posted 9 months ago

Thank you again Rohit. As I explained earlier, we need 10 (or n) equations to solve for prices (n variables). We need to repeat the problem for different ranges of the parameters ai and bi (and possibly others). In any case, I appreciate your help. Do you mind if I come back again for clarification just in case?

Sami,

Is this what you want?

supplyEqn[x_] := supply[x] == a[x] + p[x]^b[x]

Get a list of equations with

In[3]:= eqns = Table[supplyEqn[n], {n, 1, 3}]

Out[3]= {supply[1] == a[1] + p[1]^b[1], supply[2] == a[2] + p[2]^b[2],
  supply[3] == a[3] + p[3]^b[3]}

Now you can use Solve, Minimize, etc. on those equations.

I hope this helped.

Regards,

Neil

Posted 9 months ago

Wonderful, Neil! Thanks a lot! I'll try it and let you know ...

Posted 9 months ago

Neil: Here is how it worked for me.

Assume 2 markets, each with one supply and one demand function. Total of four functions. Of course, the number of markets, n, can be adjusted easily.

In[1]:= SupplyEquation[x_] := s1[x]*p[x]^s2[x]

In[2]:= SupplyFunctions = Table[SupplyEquation[n], {n, 1, 2}]

Out[2]= {p[1]^s2[1] s1[1], p[2]^s2[2] s1[2]}

In[3]:= DemandEquation[x_] := d1[x]*p[x]^d2[x]

In[4]:= DemandFunctions = Table[DemandEquation[n], {n, 1, 2}]

Out[4]= {d1[1] p[1]^d2[1], d1[2] p[2]^d2[2]}

In[5]:= Solve[DemandFunctions[[1]] == SupplyFunctions[[1]] && 
  DemandFunctions[[2]] == SupplyFunctions[[2]], {p[1], p[2]}]

Out[5]= {{p[1] -> E^((-Log[d1[1]] + Log[s1[1]])/(d2[1] - s2[1])), 
  p[2] -> E^((-Log[d1[2]] + Log[s1[2]])/(d2[2] - s2[2]))}}
Posted 9 months ago
supply[x_] := s1[x]*p[x]^s2[x]
demand[x_] := d1[x]*p[x]^d2[x]
With[{n = 2},
    Solve[
        And @@ ((supply[#] == demand[#]) & /@ Range[n]),
        p[#] & /@ Range[n]
    ]
]

Sami, I think this is a more concise way to express what you need ;)

Have a wonderful New Year,

lorenzo

Sami,

I would suggest generating your equations with:

eqns = Table[DemandEquation[i] == SupplyEquation[i], {i, 1, 2}]

or

eqns = MapThread[Equal, {DemandFunctions, SupplyFunctions}]

You can get the list of variables as the number of equations grows:

vars = Table[p[n], {n, 1, 2}]

And solve with

Solve[eqns, vars]
Posted 9 months ago

Excellent! Many thanks, Neil and Lorenzo. Happy new year to all.

Posted 9 months ago

One more question if our good friends don't mind.

How can I use "eqns" as a set of constraints in a minimization problem? Recall that:

eqns = Table[DemandEquation[i] == SupplyEquation[i], {i, 1, n}]

where n could be 2 or 3 or more. A constraint requires "And" or "&&" between the equations, but I could not put these equations together using &&. Any suggestions?

Best

Sami,

First of all you do not need the &&. Minimize will accept a list of equations instead. Second, you can get what you want with && by doing this:

eqns = Table[DemandEquation[i] == SupplyEquation[i], {i, 1, n}] /. List->And

You are essentially replacing the head List with the head And. To understand this better read about Head in the documentation. Also if you look at

eqns//FullForm

you will see the internal representation of the expression. Do this before and after the replacement above and it should be more clear.

Regards,

Neil

Posted 9 months ago

You are right Neil. I think I made some mistakes the first time and got an error message. Now it works fine. Many thanks.

At the risk of abusing your generosity, I have one more question.

If I compute the minimization problem (or solve simultaneous equations problem), I get a set of results for the specified variables, e.g.

{p[1] -> 1.71304, p[2] -> 1.66576, p[3] -> 1.58799, 
 alpha[1, 2] -> 0.273479, alpha[1, 3] -> 0.386724, 
 alpha[2, 1] -> 0.331958, alpha[2, 3] -> 0.613276, 
 alpha[3, 1] -> 0.668042, alpha[3, 2] -> 0.726521}

Now, I need to substitute for these results, i.e. set

p[1] = 1.7130407333027033`
p[2] = 1.6657564453986469`
p[3] = 1.5879949741053119`
alpha[1, 2] = 0.273478839300758`
alpha[1, 3] = 0.3867235962022603`
alpha[2, 1] = 0.3319579814272776`
alpha[2, 3] = 0.6132764037035208`
alpha[3, 1] = 0.6680420181563871`
alpha[3, 2] = 0.7265211604700595`

I am doing it now manually. Is there a way to automate this process?

Thanks in advance for your help.

Best

Sami,

Glad it helped.

The solutions are in the form of rules (i.e. a->5.3). Rules are setup for use with the Replace[] function. The best way to use this is to do what you are doing now and get your solution in the form of a list of Rules:

sol = Solve[...]

Then apply the solution to some expression

numbersolution = expr /. sol

Now numbersolution will be expr with all the variables replaced with numbers.

Another option is to define the variables globally (although I really do not like to do this -- I like to control when I substitute variables for numbers)

sol /. Rule->Set

This causes Mathematica to change the rules to a bunch of immediate assignments using Set[] (the single equal is its shortcut) -- not to be confused with double equal which is Equal (==). Set[] globally defines the variables. Again, this is usually not my first choice but if you just want them to become numerical in some circumstances it can be helpful.

Regards,

Neil

BTW, The second approach is what you are essentially doing now so that might be what you want.

The problem with the Set approach (and what you are doing now) is that to rerun the notebook you must clear the Global symbols or quit the kernel. I like to write code that can be rerun in place on the existing kernel (which is why I like to control the numerical replacements)

Regards,

Neil

Posted 9 months ago

Very good. The second approach is what I am doing now--you are right. I agree with your concerns though, and I have to frequently quit to avoid spurious results.

BTY, why not write a book on Mathematica applications (if you haven't done so already)? I am sure it would be very helpful!

Reply to this discussion
Community posts can be styled and formatted using the Markdown syntax.
Reply Preview
Attachments
Remove
or Discard

Group Abstract Group Abstract