====== 計算プログラム ====== Microsoft ExcelのVBAのプログラム Option Explicit Private Const nix As Integer = 31 Private Const ndx As Integer = 8 Private Const nout As Integer = 20 Private h(nix) As Double Private z(nix) As Double Private hs(nix) As Double Private b(nix) As Double Private x(nix) As Double Private us(nix) As Double Private sib(nix, ndx) As Double Private sib0(nix, ndx) As Double Private a(nix) As Double Private u(nix) As Double Private si(nix) As Double Private tsm(nix) As Double Private dd(ndx) As Double Private d(ndx) As Double Private p0(nix, ndx) As Double Private p(nix, ndx) As Double Private w0(ndx) As Double Private uci(ndx) As Double Private tsci0(ndx) As Double Private tsi(nix, ndx) As Double Private wc(nix) As Double Private d10(nix) As Double Private d50(nix) As Double Private d90(nix) As Double Private dm(nix) As Double Private dzdt(nix) As Double Private ct(nix) As Double Private tscm(nix) As Double Private qb(nix) As Double Private qbi(nix, ndx) As Double Private qs(nix) As Double Private qsi(nix, ndx) As Double Private c(nix, ndx) As Double Private cb(nix, ndx) As Double Private dm0(nix) As Double Private z0(nix) As Double Private sn(nix) As Double Private dx(nix) As Double Public Sub pro1d() 'パラメータ Const g As Double = 9.8 Const s As Double = 1.65 Const ram As Double = 0.4 Const delta As Double = 0.1 Const bs0 As Double = 0.143 Const snu As Double = 0.000001 Const rs As Double = 1.436 Const sk As Double = 0.008 Const als As Double = 0.14 Dim i As Integer, j As Integer, k As Integer Dim ni As Integer ', dx As Double Dim ax As Double Dim sechour As Double Dim tuk As Double Dim etime As Double Dim dtmax As Double Dim al23 As Double Dim nd As Integer Dim ttime As Double Dim qq As Double Dim h00 As Double Dim d10_0 As Double, d50_0 As Double, d90_0 As Double Dim tt As Double Dim ucm As Double Dim aa As Double, bb As Double, cc As Double Dim fh As Double, fdh As Double, dh As Double Dim xi As Double Dim tsci As Double Dim usci As Double, xxi As Double Dim bs As Double Dim ome As Double Dim bet As Double Dim alfx As Double Dim amax As Double Dim dqb As Double Dim ah As Double Dim bh1 As Double, bh2 As Double, bh3 As Double Dim bh As Double, abh As Double Dim tmax As Double Dim dt As Double Dim dz As Double Dim dqbi As Double, dpi As Double Dim ncount As Long, mcount As Long, mcol As Integer Dim ws_out As Worksheet Dim ws_zd As Worksheet Dim ws_h As Worksheet Dim ws_z As Worksheet Dim ws_dm As Worksheet, ws_d10 As Worksheet, ws_d50 As Worksheet, ws_d90 As Worksheet Set ws_out = Sheets("計算結果") Set ws_zd = Sheets("河床変動量") Set ws_h = Sheets("水位") Set ws_z = Sheets("河床標高") Set ws_dm = Sheets("平均粒径") Set ws_d10 = Sheets("d10粒径") Set ws_d50 = Sheets("d50粒径") Set ws_d90 = Sheets("d90粒径") 'Call param '粒径分布は対数正規分布(8区分) For i = 1 To ndx dd(1) = 0.1 dd(2) = 0.2 dd(3) = 0.5 dd(4) = 0.7 dd(5) = 1# dd(6) = 2# dd(7) = 4# dd(8) = 10# Next i '初期値 Dim ws1 As Worksheet Set ws1 = Sheets("初期値") qq = ws1.Cells(3, "A").Text '500# h00 = ws1.Cells(3, "B").Text '3 'sn = ws1.Cells(3, "C").Text '0.025 tuk = ws1.Cells(3, "D").Text '5# etime = ws1.Cells(3, "E").Text '30# d10_0 = ws1.Cells(7, "A").Text '0.2 d50_0 = ws1.Cells(7, "B").Text '0.5 d90_0 = ws1.Cells(7, "C").Text '1# 'Call datainput '河道断面数と初期河床標高の読み込み Dim ws0 As Worksheet Set ws0 = Sheets("河道データ") ni = ws0.Cells(1, "B").Text '31 'dx = ws0.Cells(1, "C").Text '200 For i = 1 To ni 'read(17,*) b(i),z(i) b(i) = ws0.Cells(i + 2, "E").Text z(i) = ws0.Cells(i + 2, "D").Text dx(i) = ws0.Cells(i + 2, "C").Text sn(i) = ws0.Cells(i + 2, "F").Text z0(i) = z(i) d10(i) = d10_0 d50(i) = d50_0 d90(i) = d90_0 Next i '計算時間 ax = 1# / delta sechour = 3600# tuk = sechour * tuk etime = etime * sechour dtmax = tuk al23 = Log10(23#) nd = ndx - 1 For k = 2 To nd d(k) = (dd(k) + dd(k - 1)) * 0.5 / 1000# Next k For i = 1 To ni x(i) = (i - 1) * dx(i) Next i ' ' ------ initial grain size distribution ------ ' 'Call initgrain For i = 1 To ni p0(i, 1) = 0# p0(i, nd) = 1# For k = 2 To nd - 1 p0(i, k) = ppx(dd(k), d10(i), d50(i), d90(i)) Next k Next i For i = 1 To ni For k = 2 To nd sib(i, k) = p0(i, k) - p0(i, k - 1) sib0(i, k) = sib(i, k) Next k For k = 1 To nd p(i, k) = p0(i, k) Next k Next i ' ' ------ fall velocity ----- ' 'Call fallvel For k = 2 To nd If d(k) > 0.001 Then w0(k) = 32.8 * Sqr(d(k) * 100#) * 0.01 Else w0(k) = Sqr(2# / 3# * s * g * d(k) + _ (6# * snu / d(k)) ^ 2) - 6# * snu / d(k) End If Next k ' ' ------ critical shear velocity ------ ' 'Call critcalshear For k = 2 To nd Call usc(d(k), uci(k), s, snu, g) tsci0(k) = uci(k) ^ 2 / (s * g * d(k)) Next k ' '------ initial mean diameter ------ ' 'Call meandia For i = 1 To ni dm0(i) = 0# For k = 1 To nd dm0(i) = dm0(i) + d(k) * sib(i, k) Next k Next i ttime = 0# tt = tuk ' *********************************** ' 計算開始 ' *********************************** ncount = 0 '出力用のカウンタ mcol = 3 '出力用のカウンタ g100: Debug.Print "tt = "; tt ' '------ dm ------ ' 'Call meandia For i = 1 To ni dm(i) = 0# For k = 1 To nd dm(i) = dm(i) + d(k) * sib(i, k) Next k Next i ' ' ------ tau*cm ------ ' 'Call taucm For i = 1 To ni Call usc(dm(i), ucm, s, snu, g) tscm(i) = ucm ^ 2 / (s * g * dm(i)) Next i ' '------ h ------ ' 'Call height h(1) = h00 hs(1) = h(1) - z(1) For i = 2 To ni cc = -z(i - 1) + z(i) - hs(i - 1) - _ qq ^ 2 / (2# * g * b(i - 1) ^ 2 * hs(i - 1) ^ 2) _ - dx(i - 1) * sn(i - 1) ^ 2 * qq ^ 2 / _ - (2# * b(i - 1) ^ 2 * hs(i - 1) ^ (10# / 3#)) hs(i) = hs(i - 1) g120: aa = qq ^ 2 / (2# * g * b(i) ^ 2) bb = -dx(i) * sn(i) ^ 2 * qq ^ 2 / (2# * b(i) ^ 2) fh = hs(i) + aa / hs(i) ^ 2 + bb / hs(i) ^ (10# / 3#) + cc fdh = 1# - 2# * aa / hs(i) ^ 3 - 10# / 3# * bb / hs(i) ^ (13# / 3#) dh = -fh / fdh 'Debug.Print cc, hs(i), dh If Abs(dh) < 0.0001 Then GoTo g135: hs(i) = hs(i) + dh GoTo g120: g135: h(i) = z(i) + hs(i) Next i ' ' ------ a,u,si ------ ' 'Call ausi For i = 1 To ni a(i) = b(i) * hs(i) u(i) = qq / a(i) si(i) = (sn(i) * qq / b(i)) ^ 2 / hs(i) ^ 3.3333 us(i) = Sqr(g * hs(i) * si(i)) tsm(i) = us(i) ^ 2 / (s * g * dm(i)) Next i ' ' ------ qb (bed load) and qs (suspended load) ------ ' 'Call bedload For i = 1 To ni qb(i) = 0# qs(i) = 0# For k = 2 To nd tsi(i, k) = us(i) ^ 2 / (s * g * d(k)) xi = (al23 / Log10(21# * d(k) / dm(i) + 2#)) ^ 2 tsci = xi * tscm(i) If tsi(i, k) <= tsci Then qbi(i, k) = 0# qsi(i, k) = 0# Else usci = Sqr(tsci * s * g * d(k)) qbi(i, k) = sib(i, k) * 17# * Sqr(s * g * d(k) ^ 3) * _ tsi(i, k) ^ 1.5 * (1# - tsci / tsi(i, k)) * (1# - usci / us(i)) If qbi(i, k) < 1E-20 Then qbi(i, k) = 0# qb(i) = qb(i) + qbi(i, k) xxi = tsci / tsci0(k) bs = bs0 * xxi Call omega(bs, tsi(i, k), ome) qsi(i, k) = sib(i, k) * sk * (als * ome * s * g * d(k) / (rs * us(i)) - w0(k)) If qsi(i, k) < 1E-20 Then qsi(i, k) = 0# qs(i) = qs(i) + qsi(i, k) End If Next k Next i ' ' ------ cal. of c ------ ' 'Call calc For k = 2 To nd bet = 15# * w0(k) / us(ni) alfx = alf(bet) c(ni, k) = qsi(ni, k) / (w0(k) * alfx) cb(ni, k) = c(ni, k) * alfx For i = ni - 1 To 1 Step -1 bet = 15# * w0(k) / us(i) alfx = alf(bet) c(i, k) = (qq * c(i + 1, k) + dx(i) * b(i) * qsi(i, k)) / _ (qq + dx(i) * b(i) * w0(k) * alfx) If c(i, k) <= 0.0000000001 Then c(i, k) = 0# End If cb(i, k) = c(i, k) * alfx Next i Next k ' ' ------ wc, ct------ ' 'Call wcct For i = 1 To ni ct(i) = 0# wc(i) = 0# For k = 2 To nd ct(i) = ct(i) + c(i, k) wc(i) = wc(i) + w0(k) * cb(i, k) Next k Next i ' ' ------ cal. of dt ------ ' 'Call caldt amax = 0# For i = 1 To ni - 1 dqb = (qb(i + 1) * b(i + 1) - qb(i) * b(i)) / (b(i) * dx(i)) dzdt(i) = (dqb + wc(i) - qs(i)) / (1# - ram) For k = 2 To nd If (sib(i, k) = 0# Or sib(i + 1, k) = 0#) Then GoTo g130: ah = ax / (1# - ram) * qbi(i, k) / sib(i, k) bh1 = (qbi(i, k) / sib(i, k) - qbi(i + 1, k) / sib(i + 1, k)) / dx(i) bh2 = qbi(i, k) / (b(i) * sib(i, k) * dx(i)) * (b(i) - b(i + 1)) bh3 = qsi(i, k) / sib(i, k) bh = ax / (1# - ram) * (bh1 + bh2 + bh3) If dzdt(i) > 0# Then bh = bh + ax * dzdt(i) abh = ah / dx(i) + bh * 0.5 amax = max(amax, abh) g130: Next k Next i If amax > 0# Then tmax = 1# / amax dt = min(tmax, dtmax) Else dt = dtmax End If If tt + dt > tuk Then dt = tuk - tt ' '-------- output ------ ' 'Call dataoutput mcount = 0 '出力用のカウンタ If tt >= tuk Then Debug.Print "tt=", tt, "dt=", dt, "tuk=", tuk tt = 0# ' ' ------ p ------ ' For i = 1 To ni For k = 2 To nd - 1 p(i, k) = p(i, k - 1) + sib(i, k) Next k Next i ' ------ d10,d50,d90 ------ ' For i = 1 To ni For k = 2 To nd If (p(i, k) >= 0.1 And p(i, k - 1) <= 0.1) Then d10(i) = 10# ^ ( _ Log10(dd(k - 1)) + _ (0.1 - p(i, k - 1)) / (p(i, k) - p(i, k - 1)) * _ (Log10(dd(k)) - Log10(dd(k - 1)))) End If If (p(i, k) >= 0.5 And p(i, k - 1) <= 0.5) Then d50(i) = 10# ^ ( _ Log10(dd(k - 1)) + _ (0.5 - p(i, k - 1)) / (p(i, k) - p(i, k - 1)) * _ (Log10(dd(k)) - Log10(dd(k - 1)))) End If If (p(i, k) >= 0.9 And p(i, k - 1) <= 0.9) Then d90(i) = 10# ^ ( _ Log10(dd(k - 1)) + _ (0.9 - p(i, k - 1)) / (p(i, k) - p(i, k - 1)) * _ (Log10(dd(k)) - Log10(dd(k - 1)))) End If Next k Next i Debug.Print "time=", ttime / sechour '計算結果のシート出力 ncount = ncount + 1 ws_out.Cells(ncount, "A") = "time:" ws_out.Cells(ncount, "B") = Format(ttime / sechour, "######.###0") '計算結果の出力 ncount = ncount + 1 ws_out.Cells(ncount, "C") = "断面i" ws_out.Cells(ncount, "D") = "断面距離(m)" ws_out.Cells(ncount, "E") = "河床標高(m)" ws_out.Cells(ncount, "F") = "河川幅(m)" ws_out.Cells(ncount, "G") = "水位(m)" ws_out.Cells(ncount, "H") = "平均粒径(mm)" ws_out.Cells(ncount, "I") = "d10粒径(mm)" ws_out.Cells(ncount, "J") = "d50粒径(mm)" ws_out.Cells(ncount, "K") = "d90粒径(mm)" ws_out.Cells(ncount, "L") = "初期河床からの変動量(m)" '河床変動量のみ出力 mcount = mcount + 1 ws_zd.Cells(mcount, "A") = "断面i" ws_zd.Cells(mcount, "B") = "断面距離(m)" ws_zd.Cells(mcount, "C") = "河床標高(m)" '河床標高のみ出力 ws_z.Cells(mcount, "A") = "断面i" ws_z.Cells(mcount, "B") = "断面距離(m)" ws_z.Cells(mcount, "C") = "河床標高(m)" '水位のみ出力 ws_h.Cells(mcount, "A") = "断面i" ws_h.Cells(mcount, "B") = "断面距離(m)" ws_h.Cells(mcount, "C") = "河床標高(m)" '平均粒径のみ出力 ws_dm.Cells(mcount, "A") = "断面i" ws_dm.Cells(mcount, "B") = "断面距離(m)" 'd10粒径のみ出力 ws_d10.Cells(mcount, "A") = "断面i" ws_d10.Cells(mcount, "B") = "断面距離(m)" 'd50粒径のみ出力 ws_d50.Cells(mcount, "A") = "断面i" ws_d50.Cells(mcount, "B") = "断面距離(m)" 'd90粒径のみ出力 ws_d90.Cells(mcount, "A") = "断面i" ws_d90.Cells(mcount, "B") = "断面距離(m)" mcol = mcol + 1 For j = 1 To ni ncount = ncount + 1 mcount = mcount + 1 ws_out.Cells(ncount, "C") = j ws_out.Cells(ncount, "D") = Format(x(j), "####.##0") ws_out.Cells(ncount, "E") = Format(z(j), "####.##0") ws_out.Cells(ncount, "F") = Format(b(j), "####.##0") ws_out.Cells(ncount, "G") = Format(h(j), "####.##0") ws_out.Cells(ncount, "H") = Format(dm(j) * 1000#, "###.##0") ws_out.Cells(ncount, "I") = Format(d10(j), "####.##0") ws_out.Cells(ncount, "J") = Format(d50(j), "####.##0") ws_out.Cells(ncount, "K") = Format(d90(j), "####.##0") ws_out.Cells(ncount, "L") = Format(z(j) - z0(j), "####.##0") '河床変動量のみ出力 ws_zd.Cells(mcount, "A") = j ws_zd.Cells(mcount, "B") = Format(x(j), "####.##0") ws_zd.Cells(mcount, "C") = Format(z0(j), "####.##0") ws_zd.Cells(1, mcol) = "time:" & Format(ttime / sechour, "######.##0") ws_zd.Cells(mcount, mcol) = Format(z(j) - z0(j), "####.##0") '河床標高のみ出力 ws_z.Cells(mcount, "A") = j ws_z.Cells(mcount, "B") = Format(x(j), "####.##0") ws_z.Cells(mcount, "C") = Format(z0(j), "####.##0") ws_z.Cells(1, mcol) = "time:" & Format(ttime / sechour, "######.###0") ws_z.Cells(mcount, mcol) = Format(z(j), "####.##0") '水位のみ出力 ws_h.Cells(mcount, "A") = j ws_h.Cells(mcount, "B") = Format(x(j), "####.##0") ws_h.Cells(mcount, "C") = Format(z0(j), "####.##0") ws_h.Cells(1, mcol) = "time:" & Format(ttime / sechour, "######.###0") ws_h.Cells(mcount, mcol) = Format(h(j), "####.##0") '平均粒径のみ出力 ws_dm.Cells(mcount, "A") = j ws_dm.Cells(mcount, "B") = Format(x(j), "####.##0") ws_dm.Cells(1, mcol - 1) = "time:" & Format(ttime / sechour, "######.###0") ws_dm.Cells(mcount, mcol - 1) = Format(dm(j) * 1000#, "####.##0") 'd10粒径のみ出力 ws_d10.Cells(mcount, "A") = j ws_d10.Cells(mcount, "B") = Format(x(j), "####.##0") ws_d10.Cells(1, mcol - 1) = "time:" & Format(ttime / sechour, "######.###0") ws_d10.Cells(mcount, mcol - 1) = Format(d10(j), "####.##0") 'd50粒径のみ出力 ws_d50.Cells(mcount, "A") = j ws_d50.Cells(mcount, "B") = Format(x(j), "####.##0") ws_d50.Cells(1, mcol - 1) = "time:" & Format(ttime / sechour, "######.###0") ws_d50.Cells(mcount, mcol - 1) = Format(d50(j), "####.##0") 'd90粒径のみ出力 ws_d90.Cells(mcount, "A") = j ws_d90.Cells(mcount, "B") = Format(x(j), "####.##0") ws_d90.Cells(1, mcol - 1) = "time:" & Format(ttime / sechour, "######.###0") ws_d90.Cells(mcount, mcol - 1) = Format(d90(j), "####.##0") Next j End If ' ' ------ cal. of z, sib ------ ' 'Call calzsib For i = 1 To ni - 1 dz = dt * dzdt(i) z(i) = z(i) + dz For k = 2 To nd If dz > 0# Then xi = sib(i, k) Else xi = sib0(i, k) End If dqbi = (qbi(i + 1, k) * b(i + 1) - qbi(i, k) * b(i)) _ / (b(i) * dx(i)) dpi = ax * (dt / (1# - ram) * _ (dqbi + w0(k) * cb(i, k) - qsi(i, k)) - xi * dz) sib(i, k) = sib(i, k) + dpi If sib(i, k) < 0.0000000001 Then sib(i, k) = 0# Next k Next i ttime = ttime + dt tt = tt + dt If ttime > etime Then GoTo g999: GoTo g100: g999: Close ' *********************************** ' 計算終了 ' *********************************** End Sub ' ' *********************************** ' Private Sub usc(d As Double, uc As Double, s As Double, snu As Double, g As Double) Dim rst As Double rst = Sqr(s * g) * d ^ (3# / 2#) / snu If rst <= 2.14 Then uc = 0.14 * s * g * d If rst > 2.14 Then uc = (0.1235 * s * g) ^ (25# / 32#) *_ snu ^ (7# / 16#) * d ^ (11# / 32#) If rst > 54.2 Then uc = 0.034 * s * g * d If rst > 162.7 Then uc = (0.01505 * s * g) ^ (25# / 22#) * _ snu ^ (-3# / 11#) * d ^ (31# / 22#) If rst > 671# Then uc = 0.05 * s * g * d uc = Sqr(uc) End Sub ' ' *********************************** ' Private Sub omega(bs As Double, tsi As Double, ome As Double) Dim pai As Double Dim a1 As Double, a2 As Double, a3 As Double Dim ad As Double Dim t As Double, zx As Double, px As Double Dim er1 As Double, er As Double Dim xxx As Double a1 = 0.4361836 a2 = -0.1201676 a3 = 0.937298 pai = 3.141592 If tsi <= 0.0000001 Then ome = 0# Exit Sub End If ad = bs / tsi - 2# If ad >= 0# Then xxx = ad * Sqr(2#) End If If ad < 0# Then xxx = -ad * Sqr(2#) End If t = 1# / (1# + 0.33627 * xxx) zx = 1# / Sqr(2# * pai) * Exp(-xxx ^ 2# / 2#) px = 1# - zx * (a1 * t + a2 * t ^ 2 + a3 * t ^ 3) er1 = 2# - 2# * px If ad >= 0# Then er = er1 / 2# End If If ad < 0# Then er = (2# - er1) / 2# End If If (bs = 0# Or er = 0#) Then ome = 0# Else ome = tsi / bs / (2# * Sqr(pai)) * Exp(-ad ^ 2) / er + tsi * 2# / bs - 1# End If 'if(ome.lt.1e-10) ome=0. End Sub ' ' *********************************** ' Private Function alf(bet As Double) 'if bet > 20. then ' alf = bet 'else alf = bet / (1# - Exp(-bet)) 'end if End Function ' ' *********************************** ' Private Function ppx(dd As Double, d10 As Double, d50 As Double, d90 As Double) Dim s1 As Double, s2 As Double Dim x As Double s1 = 1.282 / (Log10(d90) - Log10(d50)) s2 = -1.282 / (Log10(d10) - Log10(d50)) If dd >= d50 Then x = (Log10(dd) - Log10(d50)) * s1 Else x = (Log10(dd) - Log10(d50)) * s2 End If ppx = pc(x) End Function ' ' *********************************** ' Private Function tfunc(x As Double) If x >= 0# Then tfunc = 1# / (1# + 0.33267 * x) Else tfunc = 1# / (1# - 0.33267 * x) End If End Function ' ' *********************************** ' Private Function pc(x As Double) Dim pai As Double Dim a1 As Double, a2 As Double, a3 As Double Dim tx As Double pai = 3.141592 a1 = 0.4361836 a2 = -0.1201676 a3 = 0.937298 tx = tfunc(x) If x >= 0# Then pc = 1# - 1# / Sqr(2# * pai) * _ Exp(-x ^ 2 / 2#) * (a1 * tx + a2 * tx ^ 2 + a3 * tx ^ 3) Else pc = 1# / Sqr(2# * pai) * _ Exp(-x ^ 2 / 2#) * (a1 * tx + a2 * tx ^ 2 + a3 * tx ^ 3) End If End Function ' ' *********************************** ' Private Function max(a As Double, b As Double) max = a If max < b Then max = b End Function ' ' *********************************** ' Private Function min(a As Double, b As Double) min = a If min > b Then min = b End Function Private Function Log10(ByVal Val As Double) Log10 = Log(Val) / Log(10) End Function