Embedding Stan in C++ application

467 views
Skip to first unread message

Ulf Mertens

unread,
Jul 12, 2015, 8:10:26 AM7/12/15
to stan-...@googlegroups.com
Hi,

I wanted to know whether it is possible to incorporate Stan in another C++ application. Since it is also written in C++, there should be a way. Currently, I am using RInside to call rstan but then you have all this data transferring which is time-consuming.

Thanks in advance for your help

Bob Carpenter

unread,
Jul 12, 2015, 12:48:45 PM7/12/15
to stan-...@googlegroups.com
What specifically did you want from Stan? We're about
to separate out the math library into a standalone include --- that
contains all the matrix, probability, and autodiff code.
All of the MCMC and transform and I/O code is callable through
C++, as is the translator from a Stan program to a C++ class.

- Bob
> --
> You received this message because you are subscribed to the Google Groups "Stan users mailing list" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to stan-users+...@googlegroups.com.
> For more options, visit https://groups.google.com/d/optout.

Ben Goodrich

unread,
Jul 12, 2015, 12:52:10 PM7/12/15
to stan-...@googlegroups.com, merte...@gmail.com
On Sunday, July 12, 2015 at 8:10:26 AM UTC-4, Ulf Mertens wrote:
I wanted to know whether it is possible to incorporate Stan in another C++ application. Since it is also written in C++, there should be a way. Currently, I am using RInside to call rstan but then you have all this data transferring which is time-consuming.

At the moment, this is not as easy as it should be. If you were going to invest (a lot of) effort on this, I think it would be best spent helping us with (the closed but not merged pull request)

https://github.com/stan-dev/stan/pull/1210

If essentially all Stan functions that currently take an Eigen::Matrix<> (including vectors) were to be generalized so that they could also take an Eigen::Map<>, then (after some more changes), an external application could pass Stan a pointer to its data objects (and the relevant dimensions).

Ben

Ulf Mertens

unread,
Jul 13, 2015, 9:27:12 AM7/13/15
to stan-...@googlegroups.com, merte...@gmail.com
Thanks for your comments.

@Bob: I want to repeatedly compute data (stored in std::vector or Eigen::Matrix), pass this data to Stan and then get the chains back (again, either as std::vector or Eigen::Matrix). The underlying model stays the same.

So ideally, there would be a function such as the rstan function stan() which e.g. gets the data and a model as input and outputs samples from the posterior.

Ulf

Daniel Lee

unread,
Jul 13, 2015, 9:49:04 AM7/13/15
to stan-...@googlegroups.com, merte...@gmail.com
Hi Ulf,

These functions are all callable directly from C++. See the CmdStan repository for how this is done: src/cmdstan/command.hpp, line 731:
        mcmc::sample<Model, rng_t>
          (sampler_ptr, num_warmup, num_samples, num_thin,
           refresh, true,
           writer,
           s, model, base_rng,
           prefix, suffix, std::cout,
           startTransitionCallback);

It's currently a mess in there, but we're making it better.

That samples from the posterior. If you wanted to do it single iteration at a time, you would need to dig into the sample function to see how that's done.





--

Ulf Mertens

unread,
Jul 13, 2015, 11:08:36 AM7/13/15
to stan-...@googlegroups.com, merte...@gmail.com
Thanks, this seems promising.

If it's not too much work, could you please provide a simple example-file of how to use this function?

Ulf

Daniel Lee

unread,
Jul 13, 2015, 11:21:56 AM7/13/15
to stan-...@googlegroups.com
You're in luck. We have unit tests written for that function. From the Stan repository, take a look at this test:
  src/test/unit/mcmc/sample_test.cpp



Daniel

Ulf Mertens

unread,
Jul 15, 2015, 5:01:44 AM7/15/15
to stan-...@googlegroups.com
Thanks for your help!

Sorry if I miss something, but what does this function do? How do I tell this function from which model it should sample from?

I think of a cpp function with arguments such as: model (e.g. a .stan file), iterations, chains, data (either an .txt file or a cpp object (Matrix/struct etc.).
Just like the stan() function for R.

Ulf

Bob Carpenter

unread,
Jul 15, 2015, 7:38:45 PM7/15/15
to stan-...@googlegroups.com
The .stan file is just used to generate a C++ class.
The generated class is what gets plugged into MCMC.

You have to be careful with data and transforms.

We don't really have any of this documented or organized
for C++ clients.

- Bob

Ulf Mertens

unread,
Mar 8, 2016, 4:14:17 AM3/8/16
to Stan users mailing list
Hi,

are there any news regarding the use of Stan within C++? I know it was already possible at the time I asked here but maybe it got easier since then?

Thanks
Ulf

Bob Carpenter

unread,
Mar 8, 2016, 5:39:39 PM3/8/16
to stan-...@googlegroups.com
I'm not sure what you're looking for. CmdStan runs Stan
through C++, so if you wanted to actually run something,
you could follow the pattern there. Not much has changed
at the infrastructure level other than some callbacks replacing
streams.

- Bob
> To post to this group, send email to stan-...@googlegroups.com.

John Hall

unread,
Jun 10, 2016, 3:26:00 PM6/10/16
to Stan users mailing list
I've been curious about progress on this as well.

Perhaps my curiosity is driven by my ignorance of CmdStan, but it doesn't seem like it is the the same as calling sample from within a C++ program. When thinking about C++ and Stan, I'm thinking about a similar workflow as R. Basically, I would load and modify some data, run the equivalent of the stan function from rstan in C++, and then do some followup analysis. For instance, suppose I read a large chunk of time series data from a database, I then do some processing on it, and want to do some estimation with Stan and then look at the results.

I'm not sure how easy that workflow is with CmdStan. I don't really see much guidance in the docs. My ignorant thought is that I would have to write the data to a file, but that would be some unnecessary overhead if the amount of data is large.

I'm not sure what the best practice is here. Is it possible to pipe the data? I see some questions from SO on calling exes from within C++ programs, has anyone tried this?

If CmdStan can handle this workflow, then I would be happy.

Bob Carpenter

unread,
Jun 10, 2016, 5:09:39 PM6/10/16
to stan-...@googlegroups.com
Daniel's rewriting the services layer so that it will be
like calling CmdStan only from within C++.

All the I/O is handled through callbacks. var_context
on the reading side, and various write wrappers on the output
side. That is, there's no serialization format or files
indicated at the C++ API level.

Stanc generates the Stan model class, which has a constructor
which loads data into memory through a var_context. This instantiated
model class is what's used as an argument to all the algorithms.

You can implement the writers to stream the output data wherever
you want. It gets called one draw at a time. CmdStan streams to
a file.

Let us know if you have more specific questions.

- Bob

John Hall

unread,
Jun 11, 2016, 5:47:17 PM6/11/16
to stan-...@googlegroups.com
Thanks for the reply, but TBH I'm not sure I understand it. I've seen the docs and the Getting Started page, but this particular use case does not seem covered. Maybe a CmdStan user could write a tutorial or contribute some additional details to the docs?

You received this message because you are subscribed to a topic in the Google Groups "Stan users mailing list" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/stan-users/0m1AAvjrjOw/unsubscribe.
To unsubscribe from this group and all its topics, send an email to stan-users+...@googlegroups.com.

Bob Carpenter

unread,
Jun 11, 2016, 6:57:37 PM6/11/16
to stan-...@googlegroups.com
You're right that we don't have user-facing docs for
running Stan itself. We barely have doc for running
the math library.

We'll probably write up more when we're done with the
refactoring of the services, which will hopefully be soon.

- Bob

Daniel Lee

unread,
Jun 12, 2016, 12:11:49 PM6/12/16
to stan-users mailing list
Hi John,

CmdStan has examples of how you can access the underlying Stan C++ from a C++ executable. We don't have this doc'ed because there hasn't been any real demand for it.

Ulf, to see how this is done, see stan-dev/cmdstan's src/cmdstan directory. See command.hpp (main.hpp just includes and calls command.hpp; this is going to be much simpler in the future). That's how to call Stan from C++. You obviously don't need all of it. If you just wanted to run NUTS from the command line with known file locations, it should be a 20 line executable (+ includes). I don't have the time to deal with it now, but please remind me in about a month.


Daniel


Ben Goodrich

unread,
Jun 12, 2016, 12:47:27 PM6/12/16
to Stan users mailing list
On Friday, June 10, 2016 at 3:26:00 PM UTC-4, John Hall wrote:
I'm not sure what the best practice is here. Is it possible to pipe the data? I see some questions from SO on calling exes from within C++ programs, has anyone tried this?

I don't know of anyone who has tried hard to get this to work, in part because it would be hard. But it is perhaps easier than it was a couple of weeks ago using the DLL sublibrary in Boost 1.61.0

http://www.boost.org/doc/libs/1_61_0/doc/html/boost_dll.html

I speculate that if you compiled your Stan program without a main() function (like how rstan and pystan does it) into a shared object that you could import that using Boost DLL. But it would still be a challenge to do the I/O. In particular, unless you want a CSV file of output, you would have to do something to store the draws in memory. Maybe some of the new writers stuff would help with this.

If I were doing this, I would call R from C++ using the RInside package.

Ben

John Hall

unread,
Jun 13, 2016, 10:20:39 AM6/13/16
to Stan users mailing list
Great. I will review it.

Krzysztof Sakrejda

unread,
Jun 13, 2016, 10:35:14 AM6/13/16
to Stan users mailing list
Wouldn't the .hpp file produced by stanc be the place to start? Krzysztof


On Sunday, June 12, 2016 at 12:11:49 PM UTC-4, Daniel Lee wrote:
> > To unsubscribe from this group and stop receiving emails from it, send an email to stan-users+unsubscribe@googlegroups.com.

> > To post to this group, send email to stan-...@googlegroups.com.
> > For more options, visit https://groups.google.com/d/optout.
>
> --
> You received this message because you are subscribed to a topic in the Google Groups "Stan users mailing list" group.
> To unsubscribe from this topic, visit https://groups.google.com/d/topic/stan-users/0m1AAvjrjOw/unsubscribe.
> To unsubscribe from this group and all its topics, send an email to stan-users+unsubscribe@googlegroups.com.

> To post to this group, send email to stan-...@googlegroups.com.
> For more options, visit https://groups.google.com/d/optout.
>
>
> --
> You received this message because you are subscribed to the Google Groups "Stan users mailing list" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to stan-users+unsubscribe@googlegroups.com.

> To post to this group, send email to stan-...@googlegroups.com.
> For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Stan users mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to stan-users+unsubscribe@googlegroups.com.
Reply all
Reply to author
Forward
0 new messages