0
$\begingroup$

I have a data file with two columns. Column 1 is x-values and column 2 is f(x) values. I would like to integrate f(x) with respect to x. To load the data, I do this:

mydata = ReadList["/dataset0.txt", Number, RecordLists -> True];

It reads the data file correctly. Now how do I insert the corresponding columns in a Integrate function?

$\endgroup$
  • 1
    $\begingroup$ related mathematica.stackexchange.com/q/18863/2079 $\endgroup$ – george2079 Sep 12 '17 at 1:19
  • 2
    $\begingroup$ 1) Welcome on MMA.SE, 2) that would be easier to help you with some dummy data (possiby using RandomReals, or pastebin.com), 3) you don't want to integrate, you want to approximate the integral, using data and an approximation scheme (which one? trapezoidal, etc.). $\endgroup$ – anderstood Sep 12 '17 at 1:46
  • $\begingroup$ Thank you for helpful comments $\endgroup$ – user3389597 Sep 12 '17 at 12:56
0
$\begingroup$

The link provided by @george2079 in the comments will be very useful if you run into more technical problems. I'm going to assume that it's all plain sailing, and just go through how integrating from data can work using Interpolation.

Here's some fake data with the same structure as yours:

mydata = {#, Sin[#^2]} &@RandomReal[π, 100];

which gives you a list of x-values and a list of function values (which I'm pretending is Sin[x^2]). Without an explicit expression for your function, you'll have to approximate the integral somehow. One straightforward way of doing this is with an InterpolatingFunction.

infun = Interpolation[Transpose[mydata]];
Show[ListPlot[Transpose[mydata]], 
  Plot[infun[x], Evaluate@Flatten@{x, infun["Domain"]}]]

enter image description here

Then you can Integrate infun, using the domain stored in the InterpolatingFunction

Integrate[infun[x], Evaluate@Flatten@{x, infun["Domain"]}]
(* 0.788024 *)

Compare with the actual function

Integrate[Sin[x^2], Evaluate@Flatten@{x, infun["Domain"]}]
(* 0.788037 *)

The discrepancy is due to the fact that infun is an approximation. The more data points you have, the more accurate it will be. Obviously.

Update: As @anderstood points out, you can also implement a straighforward rectangular rule on the sorted data:

mydata = {#, Sin[#^2]} &@Sort@RandomReal[\[Pi], 100];
xlist = Differences[mydata[[1]]];

Total[xlist mydata[[2, ;; -2]]] (* forward *)
Total[xlist mydata[[2, 2 ;; ]]] (* backward *)

(* 0.76924
   0.808697 *)

which may not be quite as accurate, but improves greatly for large data sets and is a couple of orders of magnitude faster.

|improve this answer|||||
$\endgroup$
  • 2
    $\begingroup$ Another approach, using a rectangular rule: mydata = {#, Sin[#^2]} &@Sort@RandomReal[\[Pi], 100]; xlist = Differences[mydata[[1]]]; Total[xlist*mydata[[2, ;; -2]]] (change to mydata[[2, 2 ;; ]] to switch between forward and backward rule). $\endgroup$ – anderstood Sep 12 '17 at 23:14
  • $\begingroup$ @anderstood Absolutely. Depending on the size of the data, the nastiness of the function, and how much speed is a factor, that might be a better method. $\endgroup$ – aardvark2012 Sep 12 '17 at 23:27
  • $\begingroup$ Thank you. This is very helpful $\endgroup$ – user3389597 Sep 15 '17 at 13:29

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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