tum-pbs / phiflow Goto Github PK
View Code? Open in Web Editor NEWA differentiable PDE solving framework for machine learning
License: MIT License
A differentiable PDE solving framework for machine learning
License: MIT License
Current implementations of the pressure solvers ignore the set periodic boundary condition.
I've tried to modify the basic notebook to run in 3d, but I'm having an issue w/tuple indexing - here's my modified notebook, could anyone advise on what the problem might be?
https://colab.research.google.com/drive/1ZapWnE6Y41lTBkg3xKZGmzuGFME4E8jH?usp=sharing
I'm trying to compile the CUDA kernels to use PhiFlow on the GPU, however, the compilation fails. For reference, I am using WSL2 with Ubuntu 20.04. This was the log file of the compilation:
/home/mclea/PhiFlow/phi/tf/cuda/src/helpers.h: In instantiation of ‘void copyDataToArray(const T*, cudaArray*, cudaSurfaceObject_t, cudaMemcpy3DParms, int, unsigned int, unsigned int, unsigned int, unsigned int, unsigned int) [with T = float; cudaSurfaceObject_t = long long unsigned int]’:
/home/mclea/PhiFlow/phi/tf/cuda/src/resample.cu.cc:313:21: required from ‘void tensorflow::ResampleTextureMemory(unsigned int, int, const unsigned int*, unsigned int, unsigned int, unsigned int, unsigned int, const T*, const T*, T*, const Boundary*) [with T = float]’
/home/mclea/PhiFlow/phi/tf/cuda/src/resample.cu.cc:347:155: required from here
/home/mclea/PhiFlow/phi/tf/cuda/src/helpers.h:323:18: warning: ‘cudaError_t cudaMemcpyToArray(cudaArray_t, size_t, size_t, const void*, size_t, cudaMemcpyKind)’ is deprecated [-Wdeprecated-declarations]
323 | cudaMemcpyToArray(cuArray, 0, 0, data + batch * xSize * ySize * zSize * components, xSize * ySize * zSize * components * sizeof(T), cudaMemcpyDeviceToDevice);
| ~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/local/cuda/bin/../targets/x86_64-linux/include/cuda_runtime_api.h:7368:46: note: declared here
7368 | extern __CUDA_DEPRECATED __host__ cudaError_t CUDARTAPI cudaMemcpyToArray(cudaArray_t dst, size_t wOffset, size_t hOffset, const void *src, size_t count, enum cudaMemcpyKind kind);
| ^~~~~~~~~~~~~~~~~
/home/mclea/PhiFlow/phi/tf/cuda/src/helpers.h:323:18: warning: ‘cudaError_t cudaMemcpyToArray(cudaArray_t, size_t, size_t, const void*, size_t, cudaMemcpyKind)’ is deprecated [-Wdeprecated-declarations]
323 | cudaMemcpyToArray(cuArray, 0, 0, data + batch * xSize * ySize * zSize * components, xSize * ySize * zSize * components * sizeof(T), cudaMemcpyDeviceToDevice);
| ~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/local/cuda/bin/../targets/x86_64-linux/include/cuda_runtime_api.h:7368:46: note: declared here
7368 | extern __CUDA_DEPRECATED __host__ cudaError_t CUDARTAPI cudaMemcpyToArray(cudaArray_t dst, size_t wOffset, size_t hOffset, const void *src, size_t count, enum cudaMemcpyKind kind);
| ^~~~~~~~~~~~~~~~~
/home/mclea/PhiFlow/phi/tf/cuda/src/helpers.h:323:18: warning: ‘cudaError_t cudaMemcpyToArray(cudaArray_t, size_t, size_t, const void*, size_t, cudaMemcpyKind)’ is deprecated [-Wdeprecated-declarations]
323 | cudaMemcpyToArray(cuArray, 0, 0, data + batch * xSize * ySize * zSize * components, xSize * ySize * zSize * components * sizeof(T), cudaMemcpyDeviceToDevice);
| ~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/local/cuda/bin/../targets/x86_64-linux/include/cuda_runtime_api.h:7368:46: note: declared here
7368 | extern __CUDA_DEPRECATED __host__ cudaError_t CUDARTAPI cudaMemcpyToArray(cudaArray_t dst, size_t wOffset, size_t hOffset, const void *src, size_t count, enum cudaMemcpyKind kind);
| ^~~~~~~~~~~~~~~~~
/home/mclea/PhiFlow/phi/tf/cuda/src/helpers.h:323:18: warning: ‘cudaError_t cudaMemcpyToArray(cudaArray_t, size_t, size_t, const void*, size_t, cudaMemcpyKind)’ is deprecated [-Wdeprecated-declarations]
323 | cudaMemcpyToArray(cuArray, 0, 0, data + batch * xSize * ySize * zSize * components, xSize * ySize * zSize * components * sizeof(T), cudaMemcpyDeviceToDevice);
| ~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/local/cuda/bin/../targets/x86_64-linux/include/cuda_runtime_api.h:7368:46: note: declared here
7368 | extern __CUDA_DEPRECATED __host__ cudaError_t CUDARTAPI cudaMemcpyToArray(cudaArray_t dst, size_t wOffset, size_t hOffset, const void *src, size_t count, enum cudaMemcpyKind kind);
| ^~~~~~~~~~~~~~~~~
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/notification.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/lib/core/notification.h:21,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/cancellation.h:22,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:27,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/notification.h:61:65: warning: ‘tensorflow::int64’ is deprecated: Use int64_t instead. [-Wdeprecated-declarations]
61 | int64 timeout_in_us);
| ^
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/types.h:31,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/numeric_types.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/allocator.h:26,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:26,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/integral_types.h:29:63: note: declared here
29 | [[deprecated("Use int64_t instead.")]] typedef ::std::int64_t int64;
| ^~~~~
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/notification.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/lib/core/notification.h:21,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/cancellation.h:22,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:27,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/notification.h:62:58: warning: ‘tensorflow::int64’ is deprecated: Use int64_t instead. [-Wdeprecated-declarations]
62 | bool WaitForNotificationWithTimeout(int64 timeout_in_us) {
| ^
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/types.h:31,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/numeric_types.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/allocator.h:26,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:26,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/integral_types.h:29:63: note: declared here
29 | [[deprecated("Use int64_t instead.")]] typedef ::std::int64_t int64;
| ^~~~~
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/notification.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/lib/core/notification.h:21,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/cancellation.h:22,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:27,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/notification.h:81:63: warning: ‘tensorflow::int64’ is deprecated: Use int64_t instead. [-Wdeprecated-declarations]
81 | int64 timeout_in_us) {
| ^
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/types.h:31,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/numeric_types.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/allocator.h:26,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:26,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/integral_types.h:29:63: note: declared here
29 | [[deprecated("Use int64_t instead.")]] typedef ::std::int64_t int64;
| ^~~~~
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor.h:24,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/device_base.h:26,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:29,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor_shape.h:305:22: warning: ‘tensorflow::int64’ is deprecated: Use int64_t instead. [-Wdeprecated-declarations]
305 | gtl::InlinedVector<int64, 4> dim_sizes() const;
| ^~~~~
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/types.h:31,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/numeric_types.h:27,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/allocator.h:26,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:26,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/platform/default/integral_types.h:29:63: note: declared here
29 | [[deprecated("Use int64_t instead.")]] typedef ::std::int64_t int64;
| ^~~~~
In file included from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor.h:25,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/device_base.h:26,
from /home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/op_kernel.h:29,
from /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc:2:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor_types.h: In member function ‘void tensorflow::internal::MaybeWith32BitIndexingImpl<Eigen::GpuDevice>::operator()(Func, Args&& ...) const’:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor_types.h:176:25: error: use of ‘auto’ in lambda parameter declaration only available with ‘-std=c++14’ or ‘-std=gnu++14’
176 | auto all = [](const auto&... bool_vals) {
| ^~~~
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor_types.h:176:34: error: expansion pattern ‘const int&’ contains no parameter packs
176 | auto all = [](const auto&... bool_vals) {
| ^~~~~~~~~
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor_types.h: In lambda function:
/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include/tensorflow/core/framework/tensor_types.h:177:22: error: ‘bool_vals’ was not declared in this scope
177 | for (bool b : {bool_vals...}) {
| ^~~~~~~~~
/usr/local/cuda/bin/nvcc /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cu.cc -o /home/mclea/PhiFlow/phi/tf/cuda/build/resample.cu.o -std=c++11 -c -D GOOGLE_CUDA=1 -x cu -Xcompiler -fPIC --expt-relaxed-constexpr -DNDEBUG -O3 -I/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include -D_GLIBCXX_USE_CXX11_ABI=0 -DEIGEN_MAX_ALIGN_BYTES=64
gcc /home/mclea/PhiFlow/phi/tf/cuda/src/resample.cc /home/mclea/PhiFlow/phi/tf/cuda/build/resample.cu.o -o /home/mclea/PhiFlow/phi/tf/cuda/build/resample.so -std=c++11 -shared -fPIC -lcudart -O3 -L/usr/local/cuda/lib64/ -I/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow/include -D_GLIBCXX_USE_CXX11_ABI=0 -DEIGEN_MAX_ALIGN_BYTES=64 -L/home/mclea/miniconda3/envs/phi_flow/lib/python3.8/site-packages/tensorflow -l:libtensorflow_framework.so.2
I cant find why this might fail, could it be my TensorFlow version?
Sometimes GPU stuff in WSL can fail because there is no nvidia driver.
Hello,
I want to create a 2D staggered grid that contains not only the spatial dimensions, but also the temporal dimension throughout the simulation. Here's how I initialized the field, and everything seems to work correctly so far. I'm not sure if this is the optimal way to do so, so please let me know if there is a better way.
velocity_single = StaggeredGrid(0, extrapolation=extrapolation.ZERO, x=32, y=32, bounds=Box(x=32, y=32))
velocity_temporal = field.stack([Noise() @ velocity_single] * 10, dim=channel("temporal"))
print(velocity_temporal)
# StaggeredGrid[(xˢ=32, yˢ=32, vectorᶜ=x,y, temporalᶜ=10), size=(x=32, y=32), extrapolation=0]
Now I'd like to create another temporal staggered grid base on the dimension of the one I just created, but initialize all the values to 0. I attempted to use SampledField.with_values
to do so, but it seems like the temporal channel dimension was not copied over.
velocity_temporal_copy = velocity_temporal.with_values(0)
print(velocity_temporal_copy)
# StaggeredGrid[(xˢ=32, yˢ=32, vectorᶜ=x,y), size=(x=32, y=32), extrapolation=0]
I'm not quite sure if this is a bug or is this the intended behaviour?
Thanks!
If we generate a random field and upsample we see that the resulting fields are transposed (if you can't see it, look at the two darker blue dots)
MRE
from phi.flow import *
from phi import math, field
math.seed(59)
p = CenteredGrid(
Noise(
batch(batch=1),
scale=0.1,
smoothness=3),
x=64,
y=64,
bounds=Box(
x=1.0,
y=1.0
)
)
half_p = field.downsample2x(p)
double_p = field.upsample2x(p)
vis.plot([
p,
half_p,
field.upsample2x(half_p),
double_p,
field.downsample2x(double_p)
],
show_color_bar=False)
Hi, when I plot a circle with radius 1
import phi.geom as geom
import phi.vis as vis
vis.plot(geom.Sphere(math.tensor([[0, 0]], math.instance(points=None), math.channel(vector='x,y')), math.tensor([1], math.instance(points=None))))
The result is a circle with radius \sqrt{2}/2:
It seems that this is caused by the fact that the radius is converted to the diameter by multiplication with sqrt(2), instead of by multiplication with 2. Replacing 1.41 with 2.0 gives a circle of the expected size:
Hi,
if I have a numpy / torch / tensorflow array that contains n points with dimension dim in the shape of (n, dim),
how would I initialize a PointCloud with that? The docs and tutorials are not really helpful for that, but only describe how to generate point clouds directly from phiflow Tensors.
Hello,
Thank you for the amazing work.
I am trying to install the toolkit using pip as instructed, but I get the following error:
ERROR: Command errored out with exit status 1: command: /home/abushah/anaconda3/envs/cfdnet/bin/python -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/tmp/pip-install-bmlg0_n6/phiflow/setup.py'"'"'; __file__='"'"'/tmp/pip-install-bmlg0_n6/phiflow/setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' egg_info --egg-base /tmp/pip-install-bmlg0_n6/phiflow/pip-egg-info cwd: /tmp/pip-install-bmlg0_n6/phiflow/ Complete output (5 lines): Traceback (most recent call last): File "<string>", line 1, in <module> File "/tmp/pip-install-bmlg0_n6/phiflow/setup.py", line 117, in <module> with open("documentation/Package_Info.md", "r") as readme: FileNotFoundError: [Errno 2] No such file or directory: 'documentation/Package_Info.md' ---------------------------------------- ERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.
Any advice on how to resolve this?
Hi,
I have been looking into DL with physics and came across this project. However, I am having some trouble using this for a dummy case in mind, the wave equation, which is a second-order PDE. In both examples given, first-order PDEs are used. Is this package meant to be used for second-order PDEs, and if so, would you be able to share some pointers?
Regards,
Daniel
Hi, first of all I love the work you are doing here. I am working on an advection-diffusion model of a scalar field C; when evaluating the diffusion term with a non-isotropic diffusivity, a vector field is returned instead of a scalar. I have discussed this issue in private with @holl-, reposting here for visibility and tracking.
Consider the following setup:
from phi.torch import flow as pf
Diffusivity = pf.CenteredGrid(
values=(.1, 1., 1.),
extrapolation=pf.extrapolation.BOUNDARY,
bounds=conc.bounds,
resolution=conc.resolution
where diffuse.explicit
the following happens:
def explicit(field: FieldType,
diffusivity: float or math.Tensor or Field,
dt: float or math.Tensor,
substeps: int = 1) -> FieldType:
amount = diffusivity * dt
if isinstance(amount, Field):
amount = amount.at(field)
for i in range(substeps):
field += amount / substeps * laplace(field).with_extrapolation(field.extrapolation)
return field
when D is a real number, this correctly evaluates:
When laplace()
method in the code above, this evaluates first
As discussed, a simple solution here is to allow a weight term in the definition of the laplace()
method, so that we could pass laplace(field, diffusivity)
and obtain a scalar field now. Is there a simple way of implementing this? I tried a couple of options but I failed when trying to integrate with your codebase. I would truly appreciate your help.
Thank you
Thanks for fixing jit-compile in branch 2.3. Unfortunately object rotation does not work there. This program crashes in branch 2.3-develop
from phi.tf.flow import *
DOMAIN = dict(x=30, y=30)
DT = 0.1
def move_obstacle(obs: Obstacle):
new_geometry = obs.geometry.shifted([1. * DT, 0])
new_geometry = new_geometry.rotated(0.1*DT)
return obs.copied_with(geometry=new_geometry)
obstacle = Obstacle(Box(x=(5, 11), y=(10, 16)), velocity=[0., 0], angular_velocity=tensor(0.1,))
velocity = StaggeredGrid(0, extrapolation.ZERO, **DOMAIN)
obstacle_mask = CenteredGrid(HardGeometryMask(obstacle.geometry), extrapolation.BOUNDARY, **DOMAIN)
pressure = None
@math.jit_compile
def step(velocity, obstacle):
velocity = advect.mac_cormack(velocity, velocity, DT)
velocity, pressure = fluid.make_incompressible(velocity, (obstacle,))
return velocity, pressure
for _ in view(velocity, obstacle_mask, play=True, namespace=globals(), port=6006).range():
obstacle = move_obstacle(obstacle)
velocity, pressure = step(velocity, obstacle)
obstacle_mask = HardGeometryMask(obstacle.geometry) @ pressure
File "/home/flow_control/obstacle_rotate.py", line 23, in
obstacle = move_obstacle(obstacle)
File "/home/flow_control/obstacle_rotate.py", line 6, in move_obstacle
new_geometry = obs.geometry.shifted([1. * DT, 0])
File "/usr/local/lib/python3.8/dist-packages/phi/geom/_geom.py", line 233, in shifted
return self.at(self.center + delta)
File "/usr/local/lib/python3.8/dist-packages/phi/geom/_transform.py", line 78, in at
return RotatedGeometry(self._geometry.at(center), self._angle)
File "/usr/local/lib/python3.8/dist-packages/phi/geom/_box.py", line 36, in at
return Cuboid(center, self._half_size)
File "/usr/local/lib/python3.8/dist-packages/phi/geom/_geom.py", line 357, in getattr
return BoundDim(self, name)
File "/usr/local/lib/python3.8/dist-packages/phi/math/magic.py", line 461, in init
raise AttributeError(f"'{type(self)}' object has no attribute '{name}'")
AttributeError: '<class 'phi.math.magic.BoundDim'>' object has no attribute '_half_size'
I am very interested in your great work. I follow your work well in coolab but I have a problem when I use 'vis.plot(gird)' in pycharm in my local computer,It crashed and said'_tkinter.TclError: invalid command name ".!navigationtoolbar2tk.!button2"',how can I sovle it ?
Cannot plot fields wrapped with vis.overlay
in different colors since f03e6bd.
This used to be supported when color
was an attribute of the field.
Can it be fixed, maybe with a different indexing of vis.plot
's color
argument?
Hi, I want to create a 3D version of the simple smoke plume but don't know how to do it. It seems that no 3D fluid demo is included in the source code...
So I just modified a couple of settings in the 2D demo codes like this:
DOMAIN = dict(x=100, y=100, z=100, bounds=Box[0:100, 0:100, 0:100])
velocity = StaggeredGrid(0, extrapolation.ZERO, **DOMAIN) # or use CenteredGrid
smoke = CenteredGrid(0, extrapolation.BOUNDARY, x=100, y=100, z=100, bounds=DOMAIN['bounds'])
INFLOW = 0.2 * CenteredGrid(SoftGeometryMask(Sphere(center=(50, 10, 50), radius=5)), extrapolation.ZERO, resolution=smoke.resolution, bounds=smoke.bounds)
pressure = None
for _ in view(smoke, velocity, 'pressure', play=False, namespace=globals()).range(warmup=1):
smoke = advect.mac_cormack(smoke, velocity, 1) + INFLOW
buoyancy_force = smoke * (0, 0.1, 0) @ velocity # resamples smoke to velocity sample points
velocity = advect.semi_lagrangian(velocity, velocity, 1) + buoyancy_force
velocity, pressure = fluid.make_incompressible(velocity, (), Solve('auto', 1e-5, 0, x0=pressure))
Compared to the original version:
DOMAIN = dict(x=64, y=64, bounds=Box[0:100, 0:100])
velocity = StaggeredGrid((0, 0), extrapolation.ZERO, **DOMAIN) # or use CenteredGrid
smoke = CenteredGrid(0, extrapolation.BOUNDARY, x=200, y=200, bounds=DOMAIN['bounds'])
INFLOW = 0.2 * CenteredGrid(SoftGeometryMask(Sphere(center=(50, 10), radius=5)), extrapolation.ZERO, resolution=smoke.resolution, bounds=smoke.bounds)
pressure = None
for _ in view(smoke, velocity, 'pressure', play=False, namespace=globals()).range(warmup=1):
smoke = advect.mac_cormack(smoke, velocity, 1) + INFLOW
buoyancy_force = smoke * (0, 0.1) @ velocity # resamples smoke to velocity sample points
velocity = advect.semi_lagrangian(velocity, velocity, 1) + buoyancy_force
velocity, pressure = fluid.make_incompressible(velocity, (), Solve('auto', 1e-5, 0, x0=pressure))
It didn't work though. Does the current version of Phiflow support 3D fluids? I was wondering how to implement and debug it...
Thanks a lot!
First of all I want to thank you for this great library. I am trying now to build library with tf_cuda option on Win10. As I have understood from setup.py
it can be compiled only with gcc
. Other variable like cuda_lib
is also unix specifed. I am not good at C++ programming. So I have the following question. Will be it enough to change the compiler from gcc
(Linux) to to cl
(Win10 Visual Studio) with adapting the line arguments? I'd appreciate any advice or tip. I am also ready to make a pull request later for win-build.
Is there anyway to scale PhiFlow across multiple GPUs?
Hello !
I have this error :
IncompatibleShapes: Cannot merge shapes [(xˢ=1024), (xˢ=1023)] because dimension 'x' exists with different sizes.
when I try to execute this code :
import phi
from phi import flow
from phi.field._field_math import spatial_gradient
import numpy as np
phi.math.set_global_precision(64)
N = 1024
u = np.ones(N)
u = flow.math.tensor(u, flow.spatial('x'))
u = flow.field.CenteredGrid(u, flow.extrapolation.PERIODIC, x=N, bounds=flow.Box['x', 0:2*np.pi])
dudx = spatial_gradient(u, type=flow.field.StaggeredGrid, gradient_extrapolation=flow.extrapolation.PERIODIC)[0]
dudx2 = spatial_gradient(dudx, type=flow.field.StaggeredGrid, gradient_extrapolation=flow.extrapolation.PERIODIC)[0]
print(u.shape) #(xˢ=1024)
print(dudx2.shape) #(xˢ=1024)
u + dudx2 # THIS LINE CAUSE THE ERROR
The error occurs only for bad combination of global_precision and N.
For example, it occurs with :
Thank you !
Hello,
I've been trying this package out and it has been a blast. Thank you for the amazing work!
I'm currently playing around with grid value convolutions and have potentially stumbled upon a bug when the padding extrapolation mode is non-ZERO. The error is AssertionError: Shape.name is only defined for shapes of rank 1. shape=(xˢ=5, yˢ=5)
Here's a piece of code to reproduce the error.
values = math.random_normal(spatial(x=64, y=64))
kernel = math.random_normal(spatial(x=5, y=5))
values_conv = math.convolve(values, kernel, extrapolation.PERIODIC)
I think a potential fix is for this line, instead of attempting to loop over a single name for dim in conv_shape.name
, loop over the names of the shape for dim in conv_shape.names
. I tested locally with the example above and the assertion error goes away. I'm not entirely sure if this is the intended behaviour though.
Lines 1759 to 1761 in 9d11b27
Thanks for taking a look!
Hi, it's me again,
I'm still using phiflow and enjoyed it so far but I'm stuck with a documentation issue.
In the jit_compile documentation page it's written the following :
Args
f
Function to be traced. All positional arguments must be of type Tensor or PhiTreeNode returning a single Tensor or PhiTreeNode.
But I can not find any information about the PhiTreeNode class in the documentation. Would be nice to include a link to the class or to remove it from the doc if deprecated. Morever, I managed to implement a jit-compiled method which arguments weren't Tensors but CenteredGrid and int, are this special case of PhiTreeNode ?
Additionally, I'm facing a problem when trying to jit-compile the advection fonction with your wrapper. The input to the advection function is a PointCloud of Tensors I want to advect with velocity field, represented as a centered grid, and which is the second parameter of the function. Given that jited_advection = flow.math.jit_compile(flow.advect.advect)
and that I try to jit-compile the advection function to improve its speed, I get the following error message which is particularly unhelpfull :
Traceback (most recent call last):
File "/home/rocremes/projects/snake-ai/src/snake_ai/physim/main.py", line 57, in deterministic_walk
point_cloud : flow.PointCloud = jited_advection(point_cloud, gradient_field, time_step)
File "/home/rocremes/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py", line 197, in __call__
self.traces[key] = self._jit_compile(key)
File "/home/rocremes/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py", line 171, in _jit_compile
PHI_LOGGER.debug(f"Φ-jit: '{f_name(self.f)}' called with new key. shapes={[s.volume for s in in_key.shapes]}, args={in_key.tree}")
File "/home/rocremes/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/field/_point_cloud.py", line 170, in __repr__
return "PointCloud[%s]" % (self.shape,)
File "/home/rocremes/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/field/_field.py", line 136, in __getattr__
return BoundDim(self, name)
File "/home/rocremes/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/magic.py", line 449, in __init__
raise AttributeError
AttributeError
Used backend : JAX
I would love to know if it's possible to jit compile the advection function and to differentiate through it.
Thank you for the time you might take to respond.
When I using phiflow for the case of "smoke_plume", I want to save the arrays of smoke and velocity so that I can continue to calculate the solution when I need. But I don't how to assign numpy array(or tensor) into CenteredGrid and StaggeredGrid object. Could help me to fix my problem?
Thanks for help!!!
Hello, authors. First of all, thank you for your amazing work!
I can see that experimental PyTorch support has been added. I am trying to use it, but face some errors. Is it meant to be used yet? If so, could you please guide me through my error?
I am trying to use PhiFlow in a PyTorch-friendly style, and am getting an error when Fluid
validates input density.
I am trying to do approximately the following:
from PhiFlow.phi.torch.flow import *
import torch
from torch.utils.data import TensorDataset, DataLoader
inputs = torch.rand(1000, 10, 10, 1)
targets = torch.rand(1000, 10, 10, 1)
dataset = TensorDataset(inputs, targets)
dataloader = DataLoader(dataset, batch_size=10)
domain = Domain([10, 10], boundaries=PERIODIC)
sz = domain.staggered_grid(0).staggered_tensor().shape
initial_velocity = torch.zeros(*sz)
initial_velocity = initial_velocity.expand(10, *initial_velocity.shape[1:])
velocity = torch.nn.Parameter(initial_velocity)
optimizer = torch.optim.Adam([velocity], lr=1e-3)
for epoch in range(10):
for batch_index, (inputs, targets) in enumerate(dataloader):
optimizer.zero_grad()
domain = Domain([10, 10], boundaries=PERIODIC)
fluid = Fluid(domain, batch_size=10, density=inputs, velocity=velocity)
fluid.density = advect.semi_lagrangian(fluid.density, fluid.velocity, dt=1)
fluid.density = diffuse(fluid.density, 1 * 0.1, substeps=1)
loss = math.l2_loss(predictions, targets)
loss.backward()
optimizer.step()
And I get the following error:
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-1-1b5462d9cefb> in <module>()
16 optimizer.zero_grad()
17 domain = Domain([10, 10], boundaries=PERIODIC)
---> 18 fluid = Fluid(domain, batch_size=10, density=inputs, velocity=velocity)
19 fluid.density = advect.semi_lagrangian(fluid.density, fluid.velocity, dt=1)
20 fluid.density = diffuse(fluid.density, 1 * 0.1, substeps=1)
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/physics/fluid.py in __init__(self, domain, density, velocity, buoyancy_factor, tags, name, **kwargs)
26
27 def __init__(self, domain, density=0.0, velocity=0.0, buoyancy_factor=0.0, tags=('fluid', 'velocityfield', 'velocity'), name='fluid', **kwargs):
---> 28 DomainState.__init__(self, **struct.kwargs(locals()))
29
30 def default_physics(self): return INCOMPRESSIBLE_FLOW
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/physics/physics.py in __init__(self, batch_size, **kwargs)
20 def __init__(self, batch_size=None, **kwargs):
21 self._batch_size = batch_size
---> 22 struct.Struct.__init__(self, **kwargs)
23
24 @struct.constant(default=())
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/struct/struct.py in __init__(self, content_type, **kwargs)
64 trait.endow(self)
65 if content_type is VALID:
---> 66 self.validate()
67
68 @derived()
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/struct/struct.py in validate(self)
156 """
157 if not skip_validate() and self.__content_type__ is INVALID:
--> 158 self.__validate__()
159 self.__content_type__ = VALID
160 return True
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/struct/struct.py in __validate__(self)
166 trait.pre_validate_struct(self)
167 for item in self.__items__:
--> 168 item.validate(self)
169 for trait in self.__traits__:
170 trait.post_validate_struct(self)
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/struct/structdef.py in validate(self, struct)
148 for trait in self.traits:
149 value = trait.pre_validated(struct, self, value)
--> 150 value = self.validation_function(struct, value)
151 for trait in self.traits:
152 value = trait.post_validated(struct, self, value)
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/physics/fluid.py in density(self, density)
36 It describes the number of particles per physical volume.
37 """
---> 38 return self.centered_grid('density', density)
39
40 @struct.variable(default=0, dependencies=DomainState.domain)
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/physics/domain.py in centered_grid(self, name, value, components, dtype)
241 def centered_grid(self, name, value, components=1, dtype=np.float32):
242 extrapolation = Material.extrapolation_mode(self.domain.boundaries)
--> 243 return self.domain.centered_grid(value, dtype=dtype, name=name, components=components, batch_size=self._batch_size, extrapolation=extrapolation)
244
245 def staggered_grid(self, name, value, dtype=np.float32):
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/physics/domain.py in centered_grid(self, data, components, dtype, name, batch_size, extrapolation)
138 grid._age = 0.0
139 else:
--> 140 grid = CenteredGrid.sample(data, self, batch_size=batch_size)
141 assert grid.component_count == components, "Field has %d components but %d are required for '%s'" % (grid.component_count, components, name)
142 if math.dtype(grid.data) != dtype:
~/.virtualenvs/torch1venv3/lib/python3.6/site-packages/phiflow-1.4.0-py3.6.egg/phi/physics/field/grid.py in sample(value, domain, batch_size, name)
53 else: # value is constant
54 components = math.staticshape(value)[-1] if math.ndims(value) > 0 else 1
---> 55 data = math.zeros((batch_size,) + tuple(domain.resolution) + (components,)) + value
56 return CenteredGrid(data, box=domain.box, extrapolation=Material.extrapolation_mode(domain.boundaries), name=name)
57
TypeError: add(): argument 'other' (position 1) must be Tensor, not numpy.ndarray
I tried to track down where exactly my Tensor becomes numpy.ndarray, but failed to do so. I am getting this error both on master and develop branches.
A couple of comments regarding the piece of code above:
phi.torch
torch.zeros()
, because math.zeros()
returns numpy.ndarrayLooking forward to your answer,
Nikolai
Hello there!
As I just discovered this package, I have been following Fluids Tutorial to see whether I could have a nice animation. Unfortunately, copying exactly the provided code do not display anything.
I get one error warning after running vis.plot(trajectory, animate='time')
(input [7] from the tutorial):
/python3.10/site-packages/matplotlib/animation.py:887: UserWarning: Animation was deleted without rendering anything. This is most likely not intended. To prevent deletion, assign the Animation to a variable, e.g. `anim`, that exists until you have outputted the Animation using `plt.show()` or `anim.save()`.
An easy fix I used was to remove plots.close(figure)
on
Line 390 in 1c14b08
Please tell me if you need more information!
Hello! I'm running the simple smoke plume demo from the examples and tried comparing the results with phi.torch vs phi.jax. The top gif shows the results I'm getting with phi.jax, and the bottom show the results with phi.torch. The only difference between the runs is from phi.jaximport flow
vs from phi.torch import flow
. The results with torch seem correct, since they agree with the CPU results. My setup is Python 3.8.10, jax==0.3.14, jaxlib==0.3.14+cuda11.cudnn82, torch==1.12.0+cu116, cuda 11.6.
Am I doing something wrong here?
Source code:
#from phi.jax import flow
from phi.torch import flow
import matplotlib.pyplot as plt
from tqdm import tqdm
from celluloid import Camera
N_TIME_STEPS = 150
def main():
velocity = flow.StaggeredGrid(
values=(0.0, 0.0),
extrapolation=0.0,
x=64,
y=64,
bounds=flow.Box(x=100, y=100),
)
smoke = flow.CenteredGrid(
values=0.0,
extrapolation=flow.extrapolation.BOUNDARY,
x=200,
y=200,
bounds=flow.Box(x=100, y=100),
)
inflow = 0.2 * flow.CenteredGrid(
values=flow.SoftGeometryMask(
flow.Sphere(
x=40,
y=9.5,
radius=5,
)
),
extrapolation=0.0,
bounds=smoke.bounds,
resolution=smoke.resolution,
)
pressure = None
@flow.math.jit_compile
def step(velocity_prev, smoke_prev, pressure, dt=1.0):
smoke_next = flow.advect.mac_cormack(smoke_prev, velocity_prev, dt) + inflow
buoyancy_force = smoke_next * (0.0, 0.1) @ velocity # resamples smoke to velocity sample points
velocity_tent = flow.advect.semi_lagrangian(velocity_prev, velocity_prev, dt) + buoyancy_force * dt
velocity_next, pressure = flow.fluid.make_incompressible(velocity_tent, (), flow.Solve('auto', 1e-5, 0, x0=pressure))
return velocity_next, smoke_next, pressure
plt.style.use("dark_background")
fig = plt.figure()
camera = Camera(fig)
for _ in tqdm(range(N_TIME_STEPS)):
velocity, smoke, pressure = step(velocity, smoke, pressure)
smoke_values_extracted = smoke.values.numpy("y,x")
plt.imshow(smoke_values_extracted, origin="lower")
camera.snap()
animation = camera.animate()
animation.save('media/smoke_plume_torch.gif')
print("Done!")
if __name__ == "__main__":
main()
Hi, I have encountered several problems while combining PhiFlow with Pytorch:
When combining PhiFlow with the self-defined PyTorch model, how to gracefully input PhiFlow grid data, and output grid data (with/without the same layout)?
I tried using field.native_call(model, grid)
and it worked. But how can I make sure the native call processes the grid data in the right dimension I trained (e.g. 'vector, y, x' or 'vector, x, y')?
What if the model's output doesn't have the same layout as the input (e.g. input 'vector, y, x' output 'y, x')?
Also, I tried converting the PhiFlow tensor to Pytorch tensor (e.g. CenterGrid velocity.values.native("vector,y,x")
, then input the Pytorch tensor into the Pytorch model. I wondered if there is a graceful way to input and output grid data for the Pytorch model.
Looking forward to your reply!
the following code cannot be executed as a cell in a jupyter notebook or python REPL:
from phi.torch.flow import *
viewer = view()
We get an error in that case:
AttributeError Traceback (most recent call last)
Input In [3], in <cell line: 37>()
33 viewer.info(f"Model loaded.")
36 prediction = CenteredGrid((0, 0), extrapolation.BOUNDARY, x=64, y=64)
---> 37 viewer = view('divergence', scene=True, namespace=globals(), select='batch')
38 save_model(0)
39 reset() # Ensure that the first run will be identical to every time reset() is called
File ~/Source/fno_inversion_2022/venv/lib/python3.9/site-packages/phi/vis/_vis.py:138, in view(play, gui, name, description, scene, keep_alive, select, framerate, namespace, log_performance, *fields, **config)
100 """
101 Show `fields` in a graphical user interface.
102
(...)
133 `Viewer`
134 """
135 default_namespace = get_user_namespace(1)
136 user_namespace = default_namespace if namespace is None else DictNamespace(namespace,
137 title=default_namespace.get_title(),
--> 138 description=default_namespace.get_description(),
139 reference=default_namespace.get_reference())
140 variables = _default_field_variables(user_namespace, fields)
141 actions = dict(ACTIONS)
File ~/Source/fno_inversion_2022/venv/lib/python3.9/site-packages/phi/vis/_user_namespace.py:175, in LocalNamespace.get_description(self)
173 return self.function.__doc__
174 else:
--> 175 return f"Function `{self.function_name}()` in '{self.module.__file__}'"
AttributeError: 'NoneType' object has no attribute '__file__'
Presumably this is because the module is undefined when we are not in a module. Would it be of interest to replace module.__file__
with something else (a hash?) in this case?
supposing I'm working solely in pytorch, can you advise on the best practice / expected use of PhiFlow in these cases?
initial_smoke = CenteredGrid(0, extrapolation.BOUNDARY, x=32, y=40, bounds=Box[0:32, 0:40])
initial_velocity = StaggeredGrid(math.zeros(batch(inflow_loc=4)), extrapolation.ZERO, x=32, y=40, bounds=Box[0:32, 0:40])
I guess I'm digging around for initial_smoke.torch_tensor() or something, I played w/initial_smoke.values()
but that seems a layer up from what I'm expecting... I could of course convert between numpy and pytorch directly by fetching the numpy tensors/arrays, but that would cause undesirable fetching between cpu and gpu...aside from the obvious breaking of autograd.
Then I'm also looking for an equivalent like torch.from_numpy(some_torch_tensor)
but to construct a trivial grid in order to use PhiFlow.
Essentially I'm trying to mix and match the functionality instead of completely integrating everything as PhiFlow. Will this be awkward w/how things are set up currently? Sorry if this is covered in docs somewhere, some of the examples seem broken for the moment.
Hello,
I'm working with PhiFlow's PyTorch backend. At the beginning of my code, I specify the GPU as my default device by the following snippet.
from phi.torch.flow import *
TORCH.set_default_device('GPU')
Suppose for example, later in my code, I'd like to track the learning history of some grids, so I'd like to move them to the CPU in order to save memory on my GPU. In native PyTorch, I'd call something like tensor.cpu()
or tensor.to("cpu")
. I'm wondering if there is an API in PhiFlow that does the same thing? I couldn't find it in the documentation, but I might be missing something here.
Looking at previous issues (#38), I came up with a workaround that looks something like the following, but it seems very cumbersome.
from phi.torch.flow import *
TORCH.set_default_device('GPU')
# Step 1 - Create a smoke grid on the GPU
test_smoke = CenteredGrid(0, extrapolation.BOUNDARY, x=resolution, y=resolution, bounds=Box(x=resolution, y=resolution))
print(test_smoke.values.native(order=test_smoke.shape).device)
# cuda:0
# Step 2 - Intermediate PyTorch tensor to move to the CPU
test_smoke_pt_tensor = test_smoke.values.native(order=test_smoke.shape).to("cpu")
print(test_smoke_pt_tensor.device)
# cpu
# Step 3 - Reconstruct the grid from the CPU tensor
test_smoke_cpu = test_smoke.with_values(tensor(test_smoke_pt_tensor, test_smoke.shape))
print(test_smoke_cpu.values.native(order=test_smoke.shape).device)
# cpu
Thanks for your help!
For example, in ./demos/smoke_plume.py
. I try to get velocity grid values
""" Smoke Plume
Hot smoke is emitted from a circular region at the bottom.
The simulation computes the resulting air flow in a closed box.
"""
from phi.flow import *
velocity = StaggeredGrid((0, 0), 0, x=64, y=64, bounds=Box(x=100, y=100)) # or CenteredGrid(...)
smoke = CenteredGrid(0, extrapolation.BOUNDARY, x=200, y=200, bounds=Box(x=100, y=100))
INFLOW = 0.2 * CenteredGrid(SoftGeometryMask(Sphere(x=50, y=9.5, radius=5)), 0, smoke.bounds, smoke.resolution)
pressure = None
# @math.jit_compile # Only for PyTorch, TensorFlow and Jax
def step(v, s, p, dt=1.):
s = advect.mac_cormack(s, v, dt) + INFLOW
buoyancy = s * (0, 0.1) @ v # resamples smoke to velocity sample points
v = advect.semi_lagrangian(v, v, dt) + buoyancy * dt
v, p = fluid.make_incompressible(v, (), Solve('auto', 1e-5, 0, x0=p))
return v, s, p
for _ in view(smoke, velocity, 'pressure', play=False, namespace=globals()).range(warmup=1):
velocity, smoke, pressure = step(velocity, smoke, pressure)
if _ == 10:
print(velocity.values.numpy('x,y'))
break
then it throw error:
AssertionError: Dimension (vectorᶜ=x,y) missing from 'order'. Got ('x', 'y') but tensor has shape (xˢ=(x=63, y=64), yˢ=(x=64, y=63), vectorᶜ=x,y).
so I have to get velocity Tensor values in this way, but it's so werid.
...
for _ in view(smoke, velocity, 'pressure', play=True, namespace=globals()).range(warmup=1):
velocity, smoke, pressure = step(velocity, smoke, pressure)
if _ == 10:
v_x = velocity.values.unstack('vector')[0].numpy('x,y')
v_y = velocity.values.unstack('vector')[1].numpy('x,y')
print(v_x.shape,v_y.shape)
break
Output:
(63, 64) (64, 63)
So, Is there any better way to get the velocity valus?
And one more question, Why the shape of grid is (63, 64) (64, 63)
instead of (64, 64) (64, 64)
?
Thanks
Currently I am trying to adapt manual_numpy_or_tf.py
demo to PyTorch, with some additional changes. However, I could not make it work with PyTorch at all. The simplified steps are:
1- Create Fluid
object, which will consist of numpy.ndarray
by default.
FLOW = Fluid(Domain([RES] * DIM, boundaries=OPEN), batch_size=BATCH_SIZE, buoyancy_factor=0.2)
2- Copy this object to PyTorch
FLOW_TORCH = torch_from_numpy(FLOW)
3- (After some unrelated operations) Sample velocity at points of density
x_rho = DENSITY.points.data
v_rho = VELOCITY.sample_at(x_rho)
Problems occur at this stage. First of all, type of x_rho
is still numpy.ndarray
, not torch.Tensor
.
Secondly, sample_at
operation throws the error:
File "/Users/oguzziya/miniconda3/envs/phiflow/lib/python3.6/site-packages/phi/torch/torch_backend.py", line 381, in cast
dtype = {np.float16: torch.float16, np.float32: torch.float32, np.float64: torch.float64, np.bool: torch.bool, np.int8: torch.int8, np.int16: torch.int16, np.int32: torch.int32, np.int64: torch.int64}[dtype]
KeyError: dtype('float32')
I would be glad to hear any opinions, possible fixes, or steps that I overlook.
Thank you
Hello!
I'm using PhiFlow with the torch backend to optimize a sequence of control forces in a fluid solver to match sequential frames in a hand-created morph animation, and I'm running into various issues.
It seems that for short sequences of frames, optimization finds a passable set of control forces, but for longer sequences of frames, the optimizer begins to throw NaNs and other errors associated with gradients of make_incompressible()
and other things (found using torch.autograd.set_detect_anomaly(True)
).
I've attached a minimal example of the issue I'm running into (using randomized tensor sequences just to keep things compact); any advice would be greatly appreciated.
minimal_err.txt
Many thanks! Phiflow is quite enjoyable to use.
Possibly I am missing something obvious.
According to the manual, and also matplotlib general practice, if we want to show multiple plots we call matplotlib.pyplot.show
multiple times. that does not work with figures generated from phi.vis
; in fact, calling show
suppresses image display:
If I want to plot two things from one notebook cell, what should I be doing?
python code to reproduce:
from phi.flow import *
from phi import math
from matplotlib import pyplot as plt
velocity1 = StaggeredGrid(
Noise(),
x=10, y=10
)
velocity2 = StaggeredGrid(
Noise(),
x=10, y=10
)
vis.plot(velocity1)
plt.show()
vis.plot(velocity2)
plt.show()
Hi,
I want to use the Phiflow to simulate the karman vortex street with rotation cylinder. But I don't really understand the demo https://github.com/tum-pbs/PhiFlow/blob/master/demos/karman_vortex_street.py.
Specifically, I don't understand how to set the boundary condition? For example, my boundary conditions are:
Thanks for your wonderful tool and thanks for your help.
Hello,
This is just a feature request to know if a function for applying obstacle boundary conditions when using diffuse.implicit
method exists.
If not, is it something that will be implemented in the future ?
For now, the only way I see to solve diffusion equation in an environment with rectangular obstacles is to use explicit scheme, a binary mask for the obstacles and multiplying both at each time step. Is there already an other way ?
Thank you.
I'm strugling to set the extrapolations of a velocity field. For example, how to set an inflow boundary condition on the left side, and neumann conditions on the others?
Among other things, I tried this:
inflow_tensor = pf.math.tensor([1., 0.], pf.channel(vector='x,y'))
extrapolations = pf.extrapolation.combine_sides(x=(pf.extrapolation.ConstantExtrapolation(inflow_tensor), pf.extrapolation.BOUNDARY),
y=(pf.extrapolation.BOUNDARY, pf.extrapolation.BOUNDARY))
But it has no effect when doing my simple fluid simulation (advect
and make_incompressible
)
Moreover I can't compile a function using this velocity field like this.
I know I can bypass this issue by setting a BOUNDARY extrapolation on each side and setting the velocity on the lower x at each step, like in the pipe demo, but physically it is not the same, especially in the make_incompressible
step. I've been trying to dig into how extrapolations are used in calculations, but I'm not yet comfortable enough with phiflow to understand it all. ^^
What is the correct way to set extrapolations?
Hi,
Currently, the doc says that the dx
argument of the math.spatial_gradient()
function is a float. However, reading into the source code, it seems that it is possible to specify different increments for different dimensions, when the dims
argument contains more than 1 dimensions.
Could the doc be updated, possibly with an example to make this clearer?
Hello, it's me again,
I open this issue because I updated my phiflow version to 2.3.2 and tried to run the following code :
import numpy as np
import jax.numpy as jnp
import matplotlib.pyplot as plt
from snake_ai.utils import Direction
from snake_ai.physim import ConvolutionWindow, GradientField
from phi.jax import flow
@flow.math.jit_compile
def explicit_diffusion(concentration : flow.field.Field, obstacle_mask : flow.field.Field, diffusivity : float, dt : float) -> flow.field.Field:
return (1-obstacle_mask) * flow.diffuse.explicit(concentration, diffusivity=diffusivity, dt=dt)
@flow.math.jit_compile
def implicit_diffusion(concentration : flow.field.Field, obstacle_mask : flow.field.Field, diffusivity : float, dt : float) -> flow.field.Field:
return (1-obstacle_mask) * flow.diffuse.implicit(concentration, diffusivity=diffusivity, dt=dt)
field = flow.CenteredGrid(flow.Noise(0.1, 0.1), x=10, y=10)
obstacle = flow.Box(x=(4,6), y=(4,6))
obstacle_mask = flow.CenteredGrid(obstacle, x=10, y=10)
initial_field = (1-obstacle_mask) * field
t=0
dt = 0.1
while t < 1:
# field = explicit_diffusion(field, obstacle_mask, diffusivity=1, dt=dt)
field = implicit_diffusion(field, obstacle_mask, diffusivity=1, dt=dt)
t+=dt
flow.vis.plot([initial_field, field])
plt.show()
As one can see, I'm using jax >= 0.3 as backend in order to JIT compile my code. It's a very basic exemple where I diffuse a random field while taking into account absorbing conditions on an obstacle in the center of the scene.
When I try to run the above code with the flow.diffuse.explicit
method it works fine, even when I decorate the function with flow.math.jit_compile
. Nevertheless, when I try to use flow.diffuse.implicit
with the jit_compile decorator, I get the following exception (I removed the JAX specific stack-trace) :
The stack trace below excludes JAX-internal frames.
The preceding is the original exception that occurred, unmodified.
--------------------
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "/home/rcremese/projects/snake-ai/src/snake_ai/draft.py", line 25, in <module>
field = implicit_diffusion(field, obstacle_mask, diffusivity=1, dt=dt)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py", line 206, in __call__
native_result = self.traces[key](*natives)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/jax/_jax_backend.py", line 168, in run_jit_f
return self.as_registered.call(jit_f, *args, name=f"run jit-compiled '{f.__name__}'")
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/backend/_backend.py", line 354, in call
return f(*args)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py", line 177, in jit_f_native
result = self.f(**kwargs, **in_key.auxiliary_kwargs) # Tensor or tuple/list of Tensors
File "/home/rcremese/projects/snake-ai/src/snake_ai/draft.py", line 14, in implicit_diffusion
return (1-obstacle_mask) * flow.diffuse.implicit(concentration, diffusivity=diffusivity, dt=dt)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/physics/diffuse.py", line 63, in implicit
return solve_linear(sharpen, y=field, solve=solve)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_optimize.py", line 524, in solve_linear
matrix, bias = f.sparse_matrix_and_bias(solve.x0, *f_args, **f_kwargs)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py", line 366, in sparse_matrix_and_bias
return self._get_or_trace(key, args, kwargs)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py", line 303, in _get_or_trace
matrix, bias = matrix_from_function(self.f, *args, **f_kwargs, auto_compress=True)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_trace.py", line 272, in matrix_from_function
result = f(**x_kwargs, **aux_args)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/physics/diffuse.py", line 59, in sharpen
return explicit(x, diffusivity, -dt, substeps=order)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/physics/diffuse.py", line 34, in explicit
delta = laplace(field, weights=amount) if 'vector' in shape(amount) else amount * laplace(field)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/field/_field.py", line 227, in __mul__
return self._op2(other, lambda d1, d2: d1 * d2)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/field/_field.py", line 295, in _op2
other = math.tensor(other)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_tensors.py", line 1753, in tensor
data = convert_(data, use_dlpack=False)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/backend/_backend.py", line 1515, in convert
nparray = current_backend.numpy(tensor)
File "/home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/jax/_jax_backend.py", line 99, in numpy
return np.array(x)
jax._src.errors.TracerArrayConversionError: The numpy.ndarray conversion method __array__() was called on the JAX Tracer object Traced<ShapedArray(float64[], weak_type=True)>with<DynamicJaxprTrace(level=1/0)>
The error occurred while tracing the function native(implicit_diffusion) at /home/rcremese/mambaforge/envs/snake-env/lib/python3.9/site-packages/phi/math/_functional.py:173 for jit. This concrete value was not available in Python because it depends on the values of the arguments natives[0] and natives[1].
See https://jax.readthedocs.io/en/latest/errors.html#jax.errors.TracerArrayConversionError
The problem arrises only when I try to JIT-compile the function because when I remove the decorator the code works fine.
If you need any supplementary information don't hesitate to contact me.
Sincerely your.
Hello authors,
I took a look at your recent ICLR2020 paper and it is very intriguing, great work!
I am wondering if the source code for the ICLR2020 paper is included in this repo? If not, are you going to release it soon?
Thank you!
Hi all,
Thanks for creating this great framework, the differentiability opens up so many possibilities! I am currently working on some control tasks where Lagrangian fluid simulation makes more sense. I know PhiFlow is a Eulerian fluid simulation, but I was wondering whether it can be somehow used for doing Lagrangian simulation. (I'm a bit new to fluid mechanics so I'm not 100% sure if this makes sense as something to do). I would really appreciate your insight. Given your familiarity with the field, I would either way appreciate any ideas on whether differentiable Lagrangian fluid simulation is possible. Or any other frameworks you know of (I know there is some work on learned simulators, but differentiable physics is naturally more robust.) Thanks very much!
Sincerely,
Arjun
Curious if you have a minimal example ala https://github.com/tum-pbs/PhiFlow/blob/master/demos/smoke_plume.py that would demonstrate pushing the simulation onto the GPU backend selected. For example I'm importing phiflow like from phi.torch.flow import *
, but not sure what the 'phiflow' way of making sure they're using cuda tensors under the hood. Should I just access the native tensors and overwrite them w/CUDA versions (by moving them in pytorch myself)?
Several parts of the math package use np.object
, which is deprecated in the latest version of numpy.
This results in an attribute error whenever the phiflow package is imported.
AttributeError: module 'numpy' has no attribute 'object'
The error can be fixed by changing np.object
usages to np.object_
as per numpy documentation
Many thanks for your great fluid simulation package!
Is it possible to use @math.jit_compile when simulation involves moving obstacles? Currently, it becomes much slower and gives a warning: WARNING:tensorflow:6 out of the last 6 calls to <function JitFunction._jit_compile..jit_f_native at 0x7fa7a14e31f0> triggered tf.function retracing. With static obstacles jit_compile works great and gives significant speedup. See code below which is adapted from the demo example:
from phi.tf.flow import *
DOMAIN = dict(x=30, y=30)
DT = 0.1
def move_obstacle(obs: Obstacle):
if (obs.geometry.center[0]) > 35:
new_geometry = Box(x=(-6, 0), y=(10, 16))
else:
new_geometry = obs.geometry.shifted([1. * DT, 0])
return obs.copied_with(geometry=new_geometry)
obstacle = Obstacle(Box(x=(5, 11), y=(10, 16)), velocity=[1., 0], angular_velocity=tensor(0,))
velocity = StaggeredGrid(0, extrapolation.ZERO, **DOMAIN)
obstacle_mask = CenteredGrid(HardGeometryMask(obstacle.geometry), extrapolation.BOUNDARY, **DOMAIN)
pressure = None
@math.jit_compile
def step(velocity, obstacle):
velocity = advect.mac_cormack(velocity, velocity, DT)
velocity, pressure = fluid.make_incompressible(velocity, (obstacle,))
return velocity, pressure
for _ in view(velocity, obstacle_mask, play=True, namespace=globals(), port=6006).range():
obstacle = move_obstacle(obstacle)
velocity, pressure = step(velocity, obstacle)
fluid.masked_laplace.tracers.clear() # we will need to retrace because the matrix changes each step. This is not needed when JIT-compiling the physics.
obstacle_mask = HardGeometryMask(obstacle.geometry) @ pressure
Hello,
I'm kind of new using PhiFlow so I might do mistakes. But, while trying to implement a very simple 2D diffusion equation with obstacles, I faced some problems.
First, it's hard from the documentation to understand how to use the GeometryMask class. For exemple, figuring out what the @ symbole is used to in the creation of an obstacle mask is hard to understand from the API documentation (ex: obs_mask = SoftGeometryMask(obstacle.geometry, balance=1) @ velocity
)
Second, there is no type checking in the apply_boundary_conditions
function for the input variable, leading to a strange TypeError: 'Obstacle' object is not iterable
when calling the function with only one istance of an Obstacle instead of a list of obstacles. Handling the case where there is only one obstacle might be usefull. Otherwise, a simple type check assert isinstance(obstacles, (tuple, list))
would do the job.
Third, why do Obstacle
and apply_boundary_conditions
are bounded to the physic.fluid
submodule and not accessible from the flow module ? Boundary conditions and obstacles can be applied outside of a CFD problem, isn't it ?
Nevertheless, thank you for your work on all of this, I'm very existed to use your package to implement PDE with JAX !
In this demo, it is explained to obtain grad of grid values.
However, I'd like to optimize the center location of inflow like this:
# informal code
inflow_location = tensor(...)
initial_inflow = CenteredGrid(Sphere(inflow_location, ...), ...)
inflow_location_grad = # I want this
inflow_location -= 1e-2 * inflow_location_grad
Is it possible?
In the Burgers Physics class, in the step_velocity method, the advection step is performed after the diffusion step, in contrast to earlier versions. Unfortunately, I am not involved deeply enough in this topic to tell if this is a bug or intended behavior; however, reversing the order seemed to resolve an issue for me where velocity field effects were not correctly applied (see code at the end). Furthermore, the current version seemed more prone to instability issues when processing large fields (e.g. field size (128,)) with low diffusion substep counts (e. g. 1).
from phi.flow import *
import numpy as np
@struct.definition()
class GaussianClash(AnalyticField):
def __init__(self, batch_size):
AnalyticField.__init__(self, rank=1)
self.batch_size = batch_size
def sample_at(self, idx, collapse_dimensions=True):
leftloc = np.random.uniform(0.2, 0.4, self.batch_size)
leftamp = np.random.uniform(0, 3, self.batch_size)
leftsig = np.random.uniform(0.05, 0.15, self.batch_size)
rightloc = np.random.uniform(0.6, 0.8, self.batch_size)
rightamp = np.random.uniform(-3, 0, self.batch_size)
rightsig = np.random.uniform(0.05, 0.15, self.batch_size)
idx = np.swapaxes(idx, 0, -1) # batch last to match random values
left = leftamp * np.exp(-0.5 * (idx - leftloc) ** 2 / leftsig ** 2)
right = rightamp * np.exp(-0.5 * (idx - rightloc) ** 2 / rightsig ** 2)
result = left + right
result = np.swapaxes(result, 0, -1)
return result
@struct.constant()
def data(self, data):
return data
@struct.definition()
class GaussianForce(AnalyticField):
def __init__(self, batch_size):
AnalyticField.__init__(self, rank=1)
self.loc = np.random.uniform(0.4, 0.6, batch_size)
self.amp = np.random.uniform(-0.05, 0.05, batch_size) * 32
self.sig = np.random.uniform(0.1, 0.4, batch_size)
def sample_at(self, idx, collapse_dimensions=True):
idx = np.swapaxes(idx, 0, -1) # batch last to match random values
result = self.amp * np.exp(-0.5 * (idx - self.loc) ** 2 / self.sig ** 2)
result = np.swapaxes(result, 0, -1)
return result
@struct.constant()
def data(self, data):
return data
domain = Domain((32,), box=box[0:1])
dt = 0.03
viscosity=0.003
s0 = BurgersVelocity(domain, velocity=GaussianClash(1), viscosity=viscosity)
f = FieldEffect(GaussianForce(1), ['velocity'])
p = Burgers()
# Only one simulation step
s0_sim = p.step(s0, dt=dt)
# Simulation step with force application
s0_sim_f = p.step(s0, dt=dt, effects=(f,))
delta = s0_sim_f.velocity.data - s0_sim.velocity.data
# Reconstructed forces
f_a = delta / dt
# Original forces of field effect
f_b = f.field.at(s0_sim.velocity).data
# Should be close to zero?
print(np.sum(np.abs(f_a - f_b)))
# Using PhiFlow 1.4.0 this produces an error < 1e-4,
# using Phiflow 1.5.1 this error usually is > 1e0
# Reversing the order of advection and diffusion in 1.5.1
# decreases the error to < 1e-4
vis animate code uses figboxes on line 75.
This was deprecated in matplotlib 3.4 and has been completely removed since.
So this running this function as shown in many tutorials will raise AttributeError: 'AxesSubplot' object has no attribute 'figbox'
error to the end user.
To return the original functionality the line will need to be altering following this issue on the matplotlib repo.
How hard would it be to enable the Mac M1/M2 GPU devices in phiflow? It seems that phiflow currently only searches the cuda backend for devices. Are the phiflow cuda kernels only used for tensorflow? Maybe it could allow the MPS backend in pytorch, if pytorch already includes kernels for grid interpolation?
I see ways to initialize velocity fields with a single shape, but can I generate several simultaneously? I'm looking to replicate some of TempoGAN's dataset with randomly initialized velocities.
How can I write the inner product between a tensor and locations on the grid?
I have in my simulation code a function
So in my code I have the following:
C = math.random_normal(batch(neurons=3), channel(vector=['x','y']))
def U_f(xs): #
r = lambda xx: C.vector['x']*xx.vector['x'] + C.vector['y']*xx.vector['y'] ##here I want to rewrite this as dot product
U = phi.math.exp( - r(xs) )
return U
DOMAIN = dict( x=nx, y=ny, bounds=Box(x=(low_x, up_x), y=(low_y, up_y) ) )
g1 = lambda xs: U_f(xs)
Ut = CenteredGrid(g1, extrapolation.ZERO, **DOMAIN)
However I would like to express the dot product
Do you have any clue on this?
Hi,
Thanks for creating the tool. I'm still learning it.
I noticed that field.spatial_gradient()
calls internally math.spatial_gradient()
, but some arguments to the latter (e.g. difference
, dims
) are not available to the former. Is there any reason these are not made available? I feel that it might be helpful to be able to specify along which dimension to compute the gradients, in a forward or centered difference manner.
Also, does it make good sense to also make spatial_gradient()
available as a method of the Field
class?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.