How to define new random numbers in a table?

I'm trying to generate a plot of a few random straigth lines in 3D using the code below:

line[s_, x_, y_, z_, u_, phi_] := {
x + s Sqrt[1 - u^2] Cos[phi],
y + s Sqrt[1 - u^2] Sin[phi],
z + s u
}

x0[n_] := RandomReal[{-10, 10}];
y0[n_] := RandomReal[{-10, 10}];
z0[n_] := RandomReal[{-10, 10}];
u0[n_] := RandomReal[{-1, 1}];
phi0[n_] := RandomReal[{0, 2 Pi}];

severalLines[s_] := Table[
line[s, x0[n], y0[n], z0[n], u0[n], phi0[n]], {n, 1, 4}]

linesGraphics =
ParametricPlot3D[severalLines[s], {s, -20, 20}, PlotPoints -> 2];

Show[linesGraphics,
PlotRange -> {{-10, 10}, {-10, 10}, {-10, 10}},
Axes -> True,
Ticks -> None,
AxesStyle -> Opacity[0.25],
AxesOrigin -> {0, 0, 0},
SphericalRegion -> True,
Method -> {"RotationControl" -> "Globe"},
ImageSize -> {700, 700}
]

This code gives a large pack of random lines and doesn't give just 4 random straight lines. What am I doing wrong with the random functions?

For a given line, the values of x0, y0, z0, u0 and phi0 should be random, but stay fixed for that line. The values should be different for a second line, and so on.

• Your n_ argument isn't even used in the body of the functions e.g: x0[n_] := RandomReal[{-10, 10}]; Nov 30 '20 at 15:06
• try linesGraphics = ParametricPlot3D[Evaluate@severalLines[s], {s, -20, 20}, PlotPoints -> 2]?
– kglr
Nov 30 '20 at 15:09
• If all you want is a few random lines, consider the much simpler Graphics3D[{InfiniteLine /@ RandomReal[{-10, 10}, {4, 2, 3}]}] where 4 is the number of lines to generate, and {-10, 10} the range of coordinates. Nov 30 '20 at 15:09
• It's also very simple to create random lines with a uniform (in the sphere) direction distribution and finite random lengths and positions like this: pastebin.com/09sx1RbX Nov 30 '20 at 15:15
• another minimal change in your code: add the option MaxRecursion -> 0 in ParametricPlot3D[...]
– kglr
Nov 30 '20 at 15:38

UseRandomPoint to generate points in a 3D-region. In this case it is a cuboid as shown in the figure below.

pts = RandomPoint[Cuboid[{-10, -10, -10}, {10, 10, 10}], {80, 2}];

Graphics3D[{
{Black, PointSize[0.01], Point /@ pts}, (* optional *)
{Thick, Hue[RandomReal[{0, 1}]], Line@#} & /@ pts
}
, Boxed -> True
, BoxRatios -> {1, 1, 1}
, Axes -> True
] • This is a fine solution assuming criteria for "random straight lines" are free - if the statistical properties implied by the original code are required it is a different question, though. On the original example all lines would be of same length. Also, in the case of original code, difference between line endpoint coodinates for a single coordinate follow uniform distribution, while the code above produces a triangular distribution (just to point out a trivial difference between solutions)... Dec 29 '21 at 13:16

Okay, I just found the easy solution. I'm back at Mathematica after a long time, so I'm really rusty!

The solution is to add memorization with this code:

x0[n_] := x0[n] = RandomReal[{-10, 10}];
y0[n_] := y0[n] = RandomReal[{-10, 10}];
z0[n_] := z0[n] = RandomReal[{-10, 10}];
u0[n_] := u0[n] = RandomReal[{-1, 1}];
phi0[n_] := phi0[n] = RandomReal[{0, 2 Pi}];

It was really that simple. Doh!

I am not sure how useful this answer is -- I am mostly trying to utilize RandomTabularDataset.

(The only advantage of this approach compared to the codes in the question and answer by @Cham is that all parameters are seen "up-front", in a table.)

SeedRandom;
numberOfLines = 5;
dsTbl =
ResourceFunction["RandomTabularDataset"][{numberOfLines, Characters["xyzup"]}, "Generators" -> Join[Table[RandomReal[{-10, 10}, #] &, 3], {RandomReal[{-1, 1}, #] &, RandomReal[{0, 2 \[Pi]}, #] &}]] Clear[ParLine, s];
ParLine[s_, pars_?AssociationQ] := {#x + s Sqrt[1 - #u^2] Cos[#p], #y + s Sqrt[1 - #u^2] Sin[#p], #z + s #u} &@pars;
ParLine[s, #] & /@ Normal[dsTbl]

(*{{-5.98607 + 0.544786 s, 9.5079 + 0.138432 s, 5.90568 + 0.82707 s},
{-2.53347 + 0.686134 s, -3.07295 + 0.727169 s, -6.31399 - 0.021085 s},
{-8.33192 + 0.0881647 s, -3.40842 - 0.805351 s, -5.89875 - 0.586206 s},
{-0.979458 - 0.196043 s, 2.68434 - 0.223576 s, -7.79644 - 0.954767 s},
{3.91067 + 0.828513 s, -6.02554 - 0.386902 s, -8.50724 - 0.404813 s}}*)
Clear[SeveralLines];
SeveralLines[s_] := ParLine[s, #] & /@ Normal[dsTbl];
ParametricPlot3D[SeveralLines[s], {s, -20, 20}, FaceGrids -> {{0, 0, -1}, {0, 1, 0}, {-1, 0, 0}}] I interpreted the code as a geometric intent to generate uniformly randomly oriented displacements of length s from points uniformly distributed inside the {-10, -10, -10}, {10, 10, 10} cuboid.

I first sample the starting points in the cuboid, then add random points on a s-sized sphere as displacement vectors. This should correspond with the intent and the statistical properties of the original code. At least the code is much simpler than the original:

With[{n = 100},
RandomPoint[Cuboid[{-10, -10, -10}, {10, 10, 10}], n] +
s RandomPoint[Sphere[], n]] //
ParametricPlot3D[#, {s, -20, 20}, BoxRatios -> Automatic] & 