#include <iostream>
#include <memory>
#include <complex>

class Slice{
public:
    Slice(unsigned long Nx, unsigned long Ny) :
    	nx(Nx),
    	ny(Ny),
    	data(std::make_shared<std::complex<double>[]>(Nx*Ny))
    {}

    Slice(unsigned long Nx, unsigned long Ny, std::shared_ptr<std::complex<double>[]> data) :
    	nx(Nx),
    	ny(Ny),
    	data(data)
    {}

private:
    unsigned long     nx;
    unsigned long     ny;
    std::shared_ptr<std::complex<double>[]> data;
};

class Volume{
public:
    Volume(unsigned long Nx, unsigned long Ny, unsigned long Nz) :
    	nx(Nx),
    	ny(Ny),
    	nz(Nz),
        data(std::make_shared<std::complex<double>[]>(Nx * Ny * Nz))
    {
    }

    Slice get_slice(unsigned long zindex)
    {
        return Slice(nx, ny, std::shared_ptr<std::complex<double>[]>(data, &data[zindex * nx * ny]));
    }
private:
    // DATA:
    unsigned long     nx;
    unsigned long     ny;
    unsigned long     nz;
    std::shared_ptr<std::complex<double>[]> data;
};



int main(){
    unsigned long Nx = 1;
    unsigned long Ny = 2;
    unsigned long Nz = 3;

    Volume testVolume(Nx,Ny,Nz);
    /* initialise data in testVolume */
    Slice slice = testVolume.get_slice(1);
}
