On Tuesday, February 08, 2011 10:00:01 am meep-discuss-request@ab-
initio.mit.edu wrote:
>
> I am writing my code in c++ and have trouble in trying to output field. I
> do not know how to set the simulation time and tell meep that field needs
> to be output at regular time steps, which is done in libctl using the
> following syntax
>
> (run-until 200
> (at-beginning output-epsilon)
> (to-appended "ez" (at-every 0.6 output-efield-z)))
>
> How would you code the above in c++ ? I am quite new to c++, thus would
> really value if someone could help me with this.
Geeth, sorry you did not get an answer for a real Meep author, but this is how
I managed to get this to work. Hopefully more experienced users will chime in
to further improve the solution, especially if I have any misunderstandings.
So the
fields.step();
method does not ask for an update interval argument, which is what you want to
provide (.6, in your example). That is because FDTD algorithms have a formula
to compute the timestep based on the grid resolution and source frequency. So
you cannot set the interval, but you can read it in the class variable:
fields.dt
I do not know that Meep can update the fields with any finer temporal
resolution, nor that you ever should, because Nyquist is already satisfied, and
Meep runs the fastest that way (I am educated guessing about this). If you
really do need finer temporal resolution, it would just be a normal time domain
upsampling interpolation, or equivalently, Nyquist interpolation. In either
case, Meep is not involved in it. I've written my code to just use fields.dt
as the sample interval, and not tried to force it to anything else.
So the actual fields update is just like in the manual:
while (fields.time() < burnin)
fields.step();
but you recognize that each update is exactly fields.dt long. Normally, I want
just a single update, so I just call
fields.step();
and I know my state is now fields.dt seconds later.
Oh, and the easy part of your question is how to read out the field. After
every timestep, iterate over the locations you want:
for (size_t t = 0; t < H.dim[0]; t++) {
fields.step();
for (size_t i = 0; i < H.dim[1]; i++) {
float x = volume.xmin() + xsize*i/(H.dim[1]-1);
for (size_t j = 0; j < H.dim[2]; j++) {
float y = volume.ymin() + ysize*j/(H.dim[2]-1);
meep::vec loc(x,y);
H[t][i][j][0] = fields.get_field(meep::Hx, loc).real();
H[t][i][j][1] = fields.get_field(meep::Hy, loc).real();
Now the dim[0] stuff and the array indexing will depend on the array class you
are using (here, I am using a boost::multi_array subclass for H that defines
dim[]). xsize and ysize are the meep::vol2d dimensions. The cool thing about
this is that the loc(x,y) vectors do *not* have to be on the grid! They can
be arbitrary locations wherever you want them, and Meep will perform the
interpolation for you.
Hope that helps. You will also need the Meep c++ manual to make complete
sense of this message.
John
_______________________________________________
meep-discuss mailing list
[email protected]
http://ab-initio.mit.edu/cgi-bin/mailman/listinfo/meep-discuss