Loading... # 方案一 ## 使用Java实现Web服务器 ### 1、技术选型 **后端技术:** | 名称 | 版本号 | | ----------------------- | ------------- | | SpringCloud | Hoxton.SR1 | | MyBatis Plus | 3.2.0 | | SpringSecurity | 2.2.2.RELEASE | | Quartz | 2.3.2 | | SpringBoot | 2.2.2.RELEASE | | springCloud Alibaba | 2.1.0.RELEASE | | Alibaba-Nacos | 2.1.0.RELEASE | | mybatis Enhance Actable | 1.1.1.RELEASE | | anji-plus captcha | 1.2.3 | **前端技术:** | 名称 | 版本号 | | ---------- | ------ | | VueJs | 2.6.10 | | element-ui | 2.13.0 | ### 2、开发工具 | 名称 | 工具 | 版本 | | ------------------ | ------------- | -------- | | **数据库** | MySql | 5.7 | | **反向代理服务器** | Nginx | | | **开发IDE** | IntelliJ IDEA | 2019.3.3 | | **数据库客户端** | HeidiSQL | 9.3 | ### 3、开发环境 - Jdk8+ - MySql5.6+ - Redis - MongoDB ### 4、详细的架构方案 [基于前后分离分布式架构方案](https://note.fanlis.xyz/wapp/pages/view/share/s/0i11Ow3QX17G2eUTYm3c7Vfs2r-o971fr4RR2Pibxe1G72ha) ## 使用Java实现求解器 以一个简单的例子来说明实现思路,当然对于不同的求解具有不同的求解思路 ### 1、高斯扩散模型 首先定义在下风向任一点(x,y,z)的污染物浓度公式如下: $$ C(x,y,z,H)=\frac{Q}{2\pi\cdot \bar{u}\sigma_y\sigma_z}exp([-\frac{y^2}{2\sigma_y^2}])\{exp[-\frac{(z-H)^2}{2\sigma_y^2}]+exp[-\frac{(z+H)^2}{2\sigma_y^2}]\} $$ 高斯模式的坐标系如图所示,其原点为排放点(无界点源或地面源)或高架源排放点在地面的投影点,x轴正向为平均风向,y轴在水平面上垂直于x轴,正向在x轴的左侧,z轴垂直于水平面xoy,向上为正向,即为右手坐标系。 大量的实验和理论研究证明,特别是对于连续源的平均烟流,其[浓度分布](https://baike.baidu.com/item/浓度分布/12601541)是符合[正态分布](https://baike.baidu.com/item/正态分布/829892)的。因此我们可以作如下假定: (1) 污染物浓度在y、z轴上的分布符合[高斯](https://baike.baidu.com/item/高斯/10149932)分布(正态分布); (2) 在全部空间中风速是均匀的、稳定的; (3) 源强是连续均匀的; (4) 在扩散过程中污染物质量是守恒的(不考虑转化)。 代码实现为: ```java //参数定义 int emission, //污染物 int wind, //风速 int stability,//大气稳定度 int diameter, //放大比例 int w, int h ``` ```java 关键绘制代码 public static BufferedImage plot2D(Component paramComponent, Graphics paramGraphics, Set2D paramSet2D, int[] paramArrayOfColor, int paramInt1, int paramInt2, int paramInt3, int paramInt4) { int j = 0; int k = paramSet2D.getMax(); int[][] arrayOfInt = paramSet2D.getSet(); int[] arrayOfInt1 = new int[paramInt3 * paramInt4]; //红色中心点的集合 List<Integer> centers = new ArrayList<Integer>(); for (int m = paramInt4 - 1; m >= 0; m--) { for (int n = 0; n < paramInt3; n++) { int i = paramArrayOfColor.length * arrayOfInt[n][m] / (k + 1); arrayOfInt1[(j++)] = paramArrayOfColor[i]; //记录红色中心点 if(m==paramInt4/2 && paramArrayOfColor[i] == new Color(255, 0, 0, Formula.alpha).getRGB()){ centers.add(n); } } } if(centers.size() > 2){ PLOT2D_CENTER.set(centers.get(centers.size()/2)); } // 根据数据集合生成内存图片 MemoryImageSource localMemoryImageSource = new MemoryImageSource(paramInt3, paramInt4, arrayOfInt1, 0, paramInt3); // 创建图片缓冲区 BufferedImage bi = new BufferedImage(paramInt3, paramInt4, BufferedImage.TYPE_3BYTE_BGR); // 获取画笔并设置透明 Graphics2D g = bi.createGraphics(); bi = g.getDeviceConfiguration().createCompatibleImage(bi.getWidth(), bi.getHeight(), Transparency.TRANSLUCENT); g.dispose(); g = bi.createGraphics(); // 写入图片到缓存区 g.drawImage(paramComponent.createImage(localMemoryImageSource), 0, 0, null); return bi; } ``` # 方案二 ## 使用Python实现Web服务器 ### 1、技术选型 **后端技术:** | 名称 | 版本号 | | ----- | ------ | | Flask | 1.1.1 | **前端技术:** | 名称 | 版本号 | | ---------- | ------ | | VueJs | 2.6.10 | | element-ui | 2.13.0 | ### 2、开发工具 | 名称 | 工具 | 版本 | | ------------------ | ------------------ | ---- | | **数据库** | MySql | 5.7 | | **反向代理服务器** | Nginx | | | **开发IDE** | Visual Studio Code | 1.47 | | **数据库客户端** | HeidiSQL | 9.3 | ### 3、开发环境 - Python3 - MySql5.6+ - Redis - MongoDB ## 使用Python实现求解器 以一个简单的例子说明实现思路,当然对于不同的求解具有不同的求解思路 ### 1、2 维线性对流 首先需要明确控制2 维线性对流的偏微分方程(PDE)为: $$ \frac{∂u}{∂t} + c \frac{∂u}{∂x} + c \frac{∂u}{∂y} = 0 $$ 离散PDE方程写作: $$ \frac{ u_{i,j}^{n+1}-u_{i,j}^n }{∆t} + c \frac{ u_{i,j}^{n}-u_{i-1,j}^n }{∆x} + c \frac{ u_{i,j}^{n}-u_{i,j-1}^n }{∆x} = 0 $$ 要求解的未知量是: $$ u_{i,j}^{n+1}=u_{i,j}^{n}-c \frac{∆t}{∆x}(u_{i,j}^n-u_{i-1,j}^n)-c \frac{∆y}{∆t} (u_{i,j}^n-u_{i,j-1}^n) $$ 将在以下初始状态下求解该方程: $$ u(x,y)=\begin{cases} 2\ for\ 0.5 \leq x,y \leq 1 \\ 1\ for\ everywhere\ else\end{cases} $$ 且边界条件: $$ u=1\ for\ \begin{cases} x=0,2 \\ y=0,2 \end{cases} $$ 代码实现为: ```python from mpl_toolkits.mplot3d import Axes3D # 3 维绘图所需的库 import numpy from matplotlib import pyplot, cm # 声明变量 nx = 81 ny = 81 nt = 100 c = 1 dx = 2 / (nx − 1) dy = 2 / (ny − 1) sigma = .2 dt = sigma * dx x = numpy.linspace(0, 2, nx) y = numpy.linspace(0, 2, ny) u = numpy.ones((ny, nx)) # 创建一个值均为1的1xn的向量 un = numpy.ones((ny, nx)) # 分配初始状态 # 设置帽子函数初始状态:u(.5<=x<=1&&.5<=y<=1)为2 u[int(.5 / dy):int(1 / dy + 1),int(.5 / dx):int(1 / dx + 1)] = 2 u = numpy.ones((ny, nx)) u[int(.5 / dy):int(1 / dy + 1), int(.5 / dx):int(1 / dx + 1)] = 2 for n in range(nt + 1): # 按 时 间 步 数 循 环 un = u.copy() row, col = u.shape for j in range(1, row): for i in range(1, col): u[j, i] = (un[j, i] − (c * dt / dx * (un[j, i] − un[j, i − 1])) − (c * dt / dy * (un[j, i] − un[j − 1, i]))) u[0, :] = 1 u[−1, :] = 1 u[:, 0] = 1 u[:, −1] = 1 # 绘制初始状态 # 图形尺寸参数可用于产生不同尺寸的图像 fig = pyplot.figure(figsize=(11, 7), dpi=100) ax = fig.gca(projection=’3d’) X, Y = numpy.meshgrid(x, y) surf2 = ax.plot_surface(X, Y, u[:], cmap=cm.viridis) pyplot.show() ``` # 方案三 ## 使用Python/Java 实现Web服务器 同方案一/方案二 ## 使用OpenFOAM 实现求解器 ### 1、OpenFOAM 简介 > **OpenFOAM** (Open Source Field Operation and Manipulation 的缩写,意为 开源的场运算和处理 软件)是对连续介质力学问题进行数值计算的C++自由软件工具包,其代码遵守[GNU通用公共许可证](https://zh.wikipedia.org/wiki/GNU通用公共许可证)。它可进行数据预处理、后处理和自定义求解器,常用于 **CFD** 领域。 ### 2. OpenFOAM使用方式 使用OpenFOAM进行CFD模拟,大致可分为 三种 类型: * 直接利用**OpenFOAM**的标准求解器,替代商业软件。优点:免费,缺点:交互性差,对使用者要求较高; * 自定义求解器,利用**OpenFOAM**的基本类库来按照自己的需求来编写针对某类应用的求解器。用户并不需要特别关心离散和求解的最底层的知识,如时间项、对流项的离散等,关注的重点是物理问题本身。在编程中,通常是顶层的求解流程的开发,不需要用户深入研习C++语言。商业软件中的所谓UDF和**OpenFOAM**是不能相提并论的; * 自定义离散方法,属于更高级的应用,如果用户更关注时间项ddt,扩散项laplacian,对流项div是如何离散的,能否有更高效更高精度的离散方法,这需要修改finiteVolume库和OpenFOAM库中对应的代码。尤其是对流项,尽管OpenFOAM已经提供了基于NVD和TVD的模板和40多种有名的高阶高精度格式,但可以预见,这仍然是不够的,毕竟对流项的离散仍然是目前CFD的重点研究方向。 --- 学习中ing 最后修改:2024 年 12 月 05 日 © 禁止转载 赞 164 如果觉得我的文章对你有用,请随意赞赏