Skip to main content

二维微可压缩流体流动问题

MathJax TeX Test Page

油藏描述

本次算例计算一个二维油藏模型,网格数20*20,油藏大小100ft*100ft*5ft,四口井分布于(5,5)、(5,15)、(15,5)(15,15),四口井分别以100\(ft^3/d\)的产量生产。油藏边界为无流动边界,初始压力5500psi,油藏压缩系数为\(1*10^{-7} 1/Pa\),初始孔隙度在0.3-0.4之间随机生成。x和y方向渗透率在0.6-0.4D之间随机生成。

流体描述

压力和粘度关系如下表所示

40005000550060006500700075008000
0.91000.92000.92430.93720.96500.94940.98121.0019
当计算压力值超出插值范围时使用表格中的最小值或者最大值进行替换。 初始油藏状态下的油体积系数为0.9,油压缩系数为\(1*10^{-9} 1/Pa\)。

方程求解

根据物质守恒方程、状态方程和达西定律,单相流动基本方程为

$$\frac{\partial }{\partial x}\left ( \beta_c \frac{A_x k_x}{\mu B} \frac{\partial p}{\partial x} \right )\Delta x + \frac{\partial }{\partial y}\left ( \beta_c \frac{A_y k_y}{\mu B} \frac{\partial p}{\partial y} \right )\Delta y - q_{sc }=\frac{V_b}{\alpha_c}\frac{\partial }{\partial t}\left ( \frac{\varphi }{B} \right )$$

\(\beta_c\)为传到率转换因子,在油田单位制下为1.127,在国际单位制下为1.

\(\alpha_c\)为体积转换系数,在油田单位制下为5.614583,在国际单位制下为1.

\(V_b\)为网格体积,\(A\)为截面积。

$$A_x = \Delta y * \Delta z$$ $$A_y = \Delta x * \Delta z$$

\(\mu\)是流体粘度,使用插值进行计算。

\(B\)为流体体积系数

$$B = \frac{B_0}{1 + c \left (p - p_0 \right )}$$

其中\(B_0\)是\(p_0\)时的体积系数,\(c\)为流体压缩系数.

\( \varphi \)为孔隙度

$$ \varphi = \varphi_0 \left [1 + c_{\varphi } \left (p - p_0 \right ) \right ]$$

\( c_{\varphi } \)为油藏压缩系数.

基本方程变形为:

$$V_b \beta_c \frac{\partial }{\partial x}\left ( \beta_c \frac{k_x}{\mu B} \frac{\partial p}{\partial x} \right ) + V_b \beta_c \frac{\partial }{\partial y}\left ( \beta_c \frac{k_y}{\mu B} \frac{\partial p}{\partial y} \right ) - q_{sc }=\frac{V_b}{\alpha_c}\frac{\partial }{\partial t}\left ( \frac{\varphi }{B} \right )$$

使用有限差分逼近

$$T_{i + \frac{1}{2}, j} \left ( p_{i+1,j} - p_{i,j}\right ) - T_{i - \frac{1}{2}, j} \left ( p_{i,j} - p_{i-1,j}\right ) + T_{i, j + \frac{1}{2}} \left ( p_{i,j+1} - p_{i,j}\right ) $$ $$- T_{i - \frac{1}{2}, j} \left ( p_{i,j} - p_{i-1,j}\right ) - q_{sc} = \Gamma_{i , j} \left( p_{i , j}^{n+1} - p_{i , j}^{n}\right )$$

其中

$$T_{i \pm \frac{1}{2},j} = \frac{2 T_{i,j} T_{i \pm 1,j} }{T_{i,j} + T_{i \pm 1,j}}$$ $$T_{i+1,j} = \frac{\Delta y \Delta z}{\Delta x} \beta_c \frac{k_x}{\mu B}_{i+1,j}$$ $$\Gamma_{i,j} = \left [ \frac{V_b}{\alpha_c \Delta t} \left ( \frac{\varphi c_\varphi}{B^n} + \frac{\varphi^n c}{B_0}\right )\right ]_{i,j}$$

由于\(\frac{1}{\mu B}\)是压力的函数,因此本方程为非线性方程。为了将方程线性化,使用上一个时间步的压力值计算T,其余地方的压力采用此时刻的值,因此本方法是采用半隐式方法进行求解。最终得到的半隐式方程为:

$$T_{i + \frac{1}{2}, j} p_{i+1,j} + T_{i - \frac{1}{2}, j} p_{i-1,j} + T_{i , j+ \frac{1}{2}} p_{i,j+1} + T_{i , j - \frac{1}{2}} p_{i,j-1} - $$ $$\left ( T_{i + \frac{1}{2}, j} + T_{i - \frac{1}{2}, j} + T_{i , j+ \frac{1}{2}} + T_{i , j - \frac{1}{2}} + \Gamma_{i,j}\right ) p_{i,j} = q_{sc} - \Gamma_{i,j} p_{i,j}^n$$

计算结果

采用时间步为60秒,开采20天后的压力分布结果如图

MatLab计算源码


%2D single phase with 4 production wells

%Basic Parameters, SI unit
clear all
dx = 5*0.3048;
dy = 5*0.3048;
dz = 5*0.3048;
nx = 20;
ny = 20;
beta_c = 1;
alpha_c = 1;
W = [5,5;5,15;15,5;15,15];      % well position
p0 = 5500*6894.76;      % original pressure 
por0 = 0.1*rand(nx*ny,1) + 0.3;
kx = (0.2*rand(nx*ny,1) + 0.4)*1e-12;       % random permeability in x direction
ky = (0.2*rand(nx*ny,1) + 0.4)*1e-12;       % random permeability in y direction
q = 200*0.3048^3/86400;     % m^3/s

p_mu = [4000;5000;5500;6000;7000;6500;7500;8000]*6894.76;
mu = [0.9100;0.9200;0.9243;0.9372;0.9650;0.9494;0.9812;1.0019]*1e-3;
B0 = 1.1;

c_phi = 1e-7;       % 地层压缩系数
c = 1e-9;           % 流体压缩系数

nt = 60*24*20;
dt = 60;

% number the grids
Grid = zeros();
N = 1;
for i = 1:nx
    for j = 1:ny
        Grid(j,i)= N;
        N = N+1;
    end
end

%Calculation
p = ones(nx*ny,nt)*p0;
T = zeros(nx*ny,nt);
G = zeros(nx*ny,nt);        % Gamma index
X = zeros(nx*ny,nx*ny);     % matrix
Y = zeros(nx*ny,1);        % right vector
u = ones(ny*nx,nt)*0.9E-3;
B = ones(ny*nx,nt)*1.1;
por = ones(ny*nx,nt)*0.3;
p_grid = zeros(ny,nx,nt);
p_grid(:,:,1) = reshape(p(:,1),ny,nx);

for t = 1:nt
    B(:,t) = B0./(1 + c_phi.*(p(:,t)-p0));   % fluid volume index
    por(:,t) = por0.*(1 + c_phi.*(p(:,t) - p0));
    T(:,t) = dz*beta_c*kx./u(:,t)./B(:,t);
    G(:,t) = dx*dy*dz/alpha_c/dt*(por0*c_phi./B(:,t) + por(:,t)*c./B0);
    
    Y = -G(:,t).*p(:,t);
    Y(Grid(W(1,1),W(1,2))) = q + Y(Grid(W(1,1),W(1,2)));
    Y(Grid(W(2,1),W(2,2))) = q + Y(Grid(W(2,1),W(2,2)));
    Y(Grid(W(3,1),W(3,2))) = q + Y(Grid(W(3,1),W(3,2)));
    Y(Grid(W(4,1),W(4,2))) = q + Y(Grid(W(4,1),W(4,2)));
    
    for i = 1:nx
        for j = 1:ny
            if p(Grid(i,j),t) >= 4000*6894.76 && p(Grid(i,j),t) <= 8000*6894.76
                u(Grid(i,j),t) = interp1(p_mu,mu,p(Grid(i,j),t),'linear')   ;  % viscosity
            elseif p(Grid(i,j),t) < 4000*6894.76
                u(Grid(i,j),t) = 0.91*1E-3;
            else
                u(Grid(i,j),t) = 1.0019*1E-3;
            end
            if mod(i,nx) == 1
                if mod(j,ny) == 1
                    X(Grid(j,i),((i-1)*ny+j)) = -2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t)) ...
                        -2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),i*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t));
                    X(Grid(j,i),((i-1)*ny+j+1)) = 2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) ;
                elseif mod(j,ny) == 0
                    X(Grid(j,i),((i-1)*ny+j)) =  -2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t))...
                        -2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),i*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t));
                    X(Grid(j,i),((i-1)*ny+j-1)) = 2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t));
                else
                    X(Grid(j,i),((i-1)*ny+j)) =  -2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t)) -...
                        2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t)) - ...
                        2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),i*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t));
                    X(Grid(j,i),((i-1)*ny+j-1)) = 2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t));
                    X(Grid(j,i),((i-1)*ny+j+1)) = 2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t));
                end
            elseif mod(i,nx) == 0
                if mod(j,ny) == 1
                    X(Grid(j,i),((i-1)*ny+j)) = -2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t)) ...
                        -2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),(i-2)*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t));
                    X(Grid(j,i),((i-1)*ny+j+1)) = 2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) ;
                elseif mod(j,ny) == 0
                    X(Grid(j,i),((i-1)*ny+j)) =  -2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t))...
                        -2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),(i-2)*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t));
                    X(Grid(j,i),((i-1)*ny+j-1)) = 2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t));
                else
                    X(Grid(j,i),((i-1)*ny+j)) =  -2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t)) -...
                        2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t)) - ...
                        2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) - G(Grid(j,i),t);
                   X(Grid(j,i),(i-2)*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t));
                    X(Grid(j,i),((i-1)*ny+j-1)) = 2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t));
                    X(Grid(j,i),((i-1)*ny+j+1)) = 2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t));
                end
            else
                if mod(j,ny) == 1
                    X(Grid(j,i),((i-1)*ny+j)) = -2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t)) - ...
                        2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t)) -...
                        2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),i*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t));
                    X(Grid(j,i),(i-2)*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t));
                    X(Grid(j,i),((i-1)*ny+j+1)) = 2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) ;
                elseif mod(j,ny) == 0
                    X(Grid(j,i),((i-1)*ny+j)) =  -2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t)) - ...
                        2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t)) -...
                        2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),i*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t));
                    X(Grid(j,i),(i-2)*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t));
                    X(Grid(j,i),((i-1)*ny+j-1)) = 2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t));
                else
                    X(Grid(j,i),((i-1)*ny+j)) =  -2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t)) - ...
                        2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t)) -...
                        2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t)) - ...
                        2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t)) - G(Grid(j,i),t);
                    X(Grid(j,i),i*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i+1),t)/(T(Grid(j,i),t)+T(Grid(j,i+1),t));
                    X(Grid(j,i),(i-2)*ny+j) = 2*T(Grid(j,i),t)*T(Grid(j,i-1),t)/(T(Grid(j,i),t)+T(Grid(j,i-1),t));
                    X(Grid(j,i),((i-1)*ny+j-1)) = 2*T(Grid(j,i),t)*T(Grid(j-1,i),t)/(T(Grid(j,i),t)+T(Grid(j-1,i),t));
                    X(Grid(j,i),((i-1)*ny+j+1)) = 2*T(Grid(j,i),t)*T(Grid(j+1,i),t)/(T(Grid(j,i),t)+T(Grid(j+1,i),t));
                end
            end
        end
    end
    
    p(:,t+1) = X\Y;
    p_grid(:,:,t+1) = reshape(p(:,t+1),ny,nx);
end

[m,n] = meshgrid(1:20);
surf(m,n,p_grid(:,:,end))       % final 3D plot

Comments

Popular posts from this blog

使用PHP Webhook方式打造Telegram Bot

一、找BotFather拿到bot token     在telegram中私聊BotFather建立自己的bot,给bot取名,名字必须要以bot结尾。建好后自己的bot就有一个唯一的token,类似下面的一串字符 164354723:AAEjT6-IyNoXjt7miD0dwa-P5VmDTtHQC8 二、确认bot响应文件的位置     在写好bot响应文件后,要把bot放在网络上的一个位置,并且这个位置必须要加密的,即以https开头的一串网址。比如响应文件的名称为telbot.php,把它放在下面这个网址的位置: https://my.webhost.com/ 164354723:AAEjT6-IyNoXjt7miD0dwa-P5VmDTtHQC8 /telbot.php 上面网址中的红色设置和bot的token一样是为了确定这个唯一的位置,当然也可以任意设置。 三、告诉Telegram响应文件的位置 Telegram用下面网址的形式来设定webhook响应方式 https://api.telegram.org/bot [myauthorization-token] /setwebhook?url= [myboturl] 按照上面的网址形式,把自己创建的bot的token以及响应文件的位置填入,然后在浏览器中运行一下即可设置成功。比如: https://api.telegram.org/bot164354723:AAEjT6-IyNoXjt7miD0dwa-P5VmDTtHQC8/setwebhook?url=https://my.webhost.com/164354723:AAEjT6-IyNoXjt7miD0dwa-P5VmDTtHQC8/telbot.php 设置成功后,页面会显示下面的内容: {"ok":true,"result":true,"description":"Webhook is already set"} 四、在Telegram中给自己的bot发消息进行验证 php响应文件例子 <?php  define('BOT_TOKEN', 'YOURBOT:TOK

MatLab中patch函数的基本用法

patch是用来构建多边形的一个基本函数。 用法一 patch(X,Y,C) patch(X,Y,Z,C) patch( 'XData' ,X, 'YData' ,Y) patch( 'XData' ,X, 'YData' ,Y, 'ZData' ,Z) 1.1 说明 patch(X,Y,C)用来构建一个或者多个可填充的多边形,其使用X和Y作为每个点的坐标值,patch将会按顺序连接每个点。如果要得到一个多边形,将X和Y设置为向量;如果要得到多个多边形,将X和Y设置为矩阵,没一列对应一个多边形。C决定多边形的颜色,可以是系统认定的字符,也可以是一个数值,也可以是RGB向量。 patch(X,Y,Z,C)用来构建三维坐标下的多边形。 patch(‘XData’,X,’YData’,Y)和patch(‘XData’,X,’YData’,Y,’ZData’,Z)的用法与patch(X,Y,C)和patch(X,Y,Z,C)的用法类似,只是不设定颜色。 1.2 例子 1.2.1 x = [ 0 1 1 0 ] ; y = [ 0 0 1 1 ] ; patch(x,y, 'red' ) x和y都是1*4的向量,表示将四个点(0,0)、(1,0)、(1,1)和(0,1)依次连接,最后闭合形成一个四边形,设定颜色为红色。 1.2.2 x2 = [ 2 5 ; 2 5 ; 8 8 ] ; y2 = [ 4 0 ; 8 2 ; 4 0 ] ; patch(x2,y2, 'green' ) x2和y2都是3*2的向量,两列表示画两个多边形。第一个多边形连接的点依次是(2,4)、(2,8)和(8,4),第二个多边形连接的点依次是(5,0)、(5,2)和(8,0),颜色设定为绿色。 1.2.3 如果上例的三角形第一个是红色,第二个是绿色,那么patch代码修改为 x2 = [ 2 5 ; 2 5 ; 8 8 ] ; y2 = [ 4 0 ; 8 2 ; 4 0 ] ; patch(x2(:, 1 ),y2(:, 1 ), 'red' ) pat

telegram中的Sci-Hub机器人,又一文献下载利器

或许你看到标题会问什么是telegram,什么是Sci-Hub?请听我一一道来。 什么是Sci-Hub Sci-Hub是一个线上 数据库 ,其上提供48,000,000篇科学学术论文和文章。网站透过“.edu”代理服务器访问相关页面,每天会上传新的论文文章。2011年,哈萨克研究生亚历珊卓·艾尔巴金(Alexandra  Elbakyan)因为研究论文成本过高,每篇论文在付费墙机制下通常需要花费30美元,而决定成立Sci-Hub。2014年,学术界开始预测网站将会发展为类似Napster的服务。不过到了2015年,学术出版社爱思唯尔向纽约地方法院提交诉讼,指控Sci-Hub已经侵犯版权。纽约地方法院在2015年10月28日仍下令Sci-Hub原本使用的网域名称“Sci-Hub.org”必须终止。爱思唯尔在法院上获得胜诉后,一群研究人员、作家和艺术家则连署一封表态支持Sci-Hub和创世纪图书馆的公开信,声称这次诉讼对于世界各地的研究人员是“重大打击”,并指出:“它同样贬低我们、作者、编辑和读者。它寄生于我们的劳动,它阻挠我们为大众服务,它阻拦我们进入。”而该计划于11月因法院命令中止后,在同一个月内便改用网域名称“.io”重新上线,并开放使用Tor浏览。2016年1月时,Sci-Hub平均每天约有200,000人访问,Sci-Hub则声称网站服务每天平均有数十万次档案请求。  Sci-Hub是目前已知第一个提供大量自动且免费的付费学术论文的网站,使用者不需要事前订阅或付款,就能够使用原本存放在付费数据库的论文文章,并提供搜寻原先出版社网站内的文件档案服务。 以上介绍来源于维基百科词条 Sci-Hub Sci-Hub网站被屡次下线,但是又通过更换域名重新上线。以下三个网址经测试可以使用:  http://www.sci-hub.bz/   http://www.sci-hub.ac/   http://www.sci-hub.cc/   广大学者将自己的文章发表至学术期刊(免费或者支付版面费),然而当需要查看其他学者的文章时还需要向出版商付费,你是不是也觉得这完全阻碍了科学文化的传播。艾尔巴金在为自己辩护时援引联合国《世界人权宣言》第二十七条所提的:“人人有权自由参加社会之文化生活,欣赏艺术,并共同襄享科学进步及其利益。”关于这个问题,另一位被称