Take the 2-minute tour ×
Mathematica Stack Exchange is a question and answer site for users of Mathematica. It's 100% free, no registration required.

This question already has an answer here:

In the following code what would be the simplest way to generalize it to say some $N_f$ number of $z$ instead of just $z_1$ and $z_2$?

$Assumptions = {1 > y > 0, 1 > z1 > 0, 1 > z2 > 0}; 
Nmax = 40; 
LnMT1 = -Sum[Log[1 - (1/(1 + x^n)) (x^(n/2) (y^(n/2) + z1^n + z2^n) + 
   x^(n/2) (y^(-n/2) + z1^(-n) + z2^(-n)))], {n, 1, Nmax}]; 
LnMT2 = Sum[(1/n) (Sum[x^(k*(n/2))*Subscript[f, k][y, z1, z2, n], 
   {k, 1, Nmax}]/(1 - x^(2*n))), {n, 1, Nmax}]; 

For[i = 1, i <= Nmax, i++, 
  temp[y_, z1_, z2_] = Simplify[Solve[SeriesCoefficient[LnMT1 - LnMT2, {x, 0, i/2}] == 0, 
     Subscript[f, i][y, z1, z2, 1]][[1, 1, 2]]]; 
  Print["coefficient of ", x^{i/2}, " = ", Expand[Simplify[temp[y, z1, z2]]]]; 
  Subscript[f, i][y_, z1_, z2_, n_] = temp[y^n, z1^n, z2^n]
]
  • I guess the places where there is a sum over the nth powers of z1 and z2, they canbe replaced by Sum[z[j]^n, {j, 1, Nf}] but the problem is with the "functions" "temp" and $f_i$ which will need to handle $N_f$ number of variables. I tried defining expressions like, g[Table[z[i], {i, 1, Nf}]] = Sum[z[j]^2, {j, 1, Nf}] but I couldn't do anything with them. And I anyway don't know how to define a function of $N_f$ variables. (..one can't pass values to the above $g$...and in the above code one would want to even functionally update $f_i$ as in the last line of the loop.

  • Also in the "Print" line when I am printing out the evaluated expression for temp often I want to print the value of temp with one or more of its variables (y and z) being set to 1. If the above code can be generalized to arbitrary number of z then how would this setting to one be done then?

Note: in all of it I am assuming that at the start there will be a new line declaring the value of $N_f$ to be used as is being done now for Nmax

share|improve this question

marked as duplicate by Mr.Wizard Aug 16 '13 at 18:01

This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.

2  
You code cannot be executed by copy&paste. Can you please recheck it and reduce it to the smallest possible part which still shows your behavior? –  halirutan Dec 13 '12 at 2:50
    
I again converted the code into "InputForm" and pasted it. I have checked that it works. –  user6818 Dec 13 '12 at 3:10

3 Answers 3

When you define a function, you use Blank to match exactly one expression. Therefore z1_ stands for match one parameter. As you might have seen, we have BlankSequence (__) and BlankNullSequence (___) too. The former matches one or more expressions, while the latter matches zero, one or more expressions. Therefore, you can define a function like

f[z__] := {z}

f[a]
f[1,{123},b,c]
f[a,b,c]
(*
  {a}
  {1,{123},b,c}
  {a,b,c}
*)

to match as many parameters as you like. You can of course do something with the parameters

g[z__] := Sum[Sqrt[elm], {elm, {z}}]
g[a,b,c,d]
(* Sqrt[a]+Sqrt[b]+Sqrt[c]+Sqrt[d] *)

You may now say *but I cannot access single z1 for instance. First, yes you can

h[y__] := With[{z = {y}}, z[[1]] + z[[5]]]
h[a, b, c, d, e]
(* a + e *)

but secondly, what would be the use of this? When I access z[[5]], the function is not general anymore, because I expect always at least 5 parameters.

share|improve this answer
    
Didn't understand how your answer corresponds to my question. Now I can define 2 variable functions like $f[z1_,z2_] := $ and I can manually keep increasing it by adding extra zs through the code by hand. What I want to do is to define $f$ such that it is a function of $Nf$ zs and be able to set the value of Nf at the beginning. –  user6818 Dec 13 '12 at 3:12
    
@user6818 Can you come to chat? –  halirutan Dec 13 '12 at 3:37
    
yes I am logged into chat –  user6818 Dec 13 '12 at 3:59

Perhaps you can use Repeated?

A function with five arguments:

  ClearAll[h];
  h[z : Repeated[_, {5}]] := Plus @@ {z}
  {h[1], h[1, 2, 3, 4, 5], h[a, b, c, d, e], h[1, 2, 3, 4, 5, 6, a]}
  (* {h[1],15,a+b+c+d+e,h[1,2,3,4,5,6,a]} *)

another example with five arguments:

   ClearAll[h2];
   h2[z : Repeated[_, {5}]] := {z}[[2]] + {z}[[3]]
   {h2[1], h2[1, 2, 3, 4, 5], h2[a, b, c, d, e], h2[1, 2, 3, 4, 5, 6, a]}
   (* {h2[1],5,b+c,h2[1,2,3,4,5,6,a]}  *)

Another alternative is to use Condition

  ClearAll[h3, h4, h5];
  mm = 5;
  h3[z___ /; Length[{z}] == mm] := Max[z]
  h4[z___] /; Length[{z}] == mm := Max[z]
  h5[z___] := Max[z] /; Length[{z}] == mm
share|improve this answer

Looking just at the question in the title without going through the rest of the code, my simple answer would be to define your functions to take exactly one argument zList at all times, where zList is a List (as the name says). This list can have any number of arguments, and the function can run through them in a way that adapts to Length[ zList ] (preferably by using constructs like Map that operate on the whole list at once).

share|improve this answer
    
The issue is with being able to treat each of these zs as variables to which values can be passed. You can see how "temp" needs to be defined in the first line of the loop and how $f_i$ is updated by temp in the last line of the loop. How would one achieve these even if I make these functions of tables of z? Also in the "Print" line I often want to print the value of temp with all of its arguments set to a value 1. How does one achieve that? –  user6818 Dec 13 '12 at 8:53

Not the answer you're looking for? Browse other questions tagged or ask your own question.