OpenSees 동적 모델은 왜 정적 모델이 묻지 않던 세 가지를 요구하는가: 질량·감쇠·시간적분
모든 주기를 조용히 31.6배 어긋나게 만드는 질량 단위, 정확 캔틸레버 진동수와 대조한 집중질량·일관질량 수렴, 평범한 캔틸레버의 세 번째 고유치가 1차 축방향 모드인 이유, Rayleigh 감쇠가 고정한 두 모드가 아니라 모든 모드에 실제로 적용하는 값, OpenSees로 검증한 Newmark 주기연
정적 모델은 이미 강성을 가지고 있다. 동적 모델은 질량과 감쇠와 시간적분기를 추가로 요구하는데, 셋 중 하나만 계측할 수 있고, 하나는 언제나 가정이며, 하나는 확인 가능한 공식을 따르는 오차를 만든다. 어느 것이 어느 것인지 아는 것이 변호할 수 있는 동적해석과 그냥 돌아간 해석을 가르는 대부분이다.
이 글은 내진기준·목표 감쇠비·지진기록 선정 절차·허용치를 제시하지 않는다. 새로 들어오는 세 객체가 무엇을 하는지, 그리고 각각을 어떻게 검증하는지를 세운다. 질량은 Euler-Bernoulli 캔틸레버 정확 진동수와 대조한 고유치로, 감쇠는 고정한 두 진동수가 아니라 모든 모드에서 평가한 Rayleigh 곡선으로, 시간적분은 Newmark 주기연장 정확식과 안정 한계로 검증한다. 그리고 초보와 숙련자를 가리지 않고 걸리는 함정 하나를 보인다. 평범한 캔틸레버의 세 번째 고유치는 세 번째 휨모드가 아니다. 모든 수치는 OpenSeesPy 3.8.0에서 생성했다. 이 글은 4부이며 1~3부(객체 모델, 탄성 라멘, 파이버 단면)를 전제한다.
1. 동적해석이 기존 모델에 더하는 것
정적 문제는 K u = p다. 동적 문제는 운동방정식이고, 새로 생기는 항마다 대응하는 명령이 있다.
코드를 쓰기 전에 실무적으로 짚을 것이 셋 있다.
질량은 힘·길이와 일관되어야 한다. OpenSees에는 단위가 없으므로 질량은 선택한 체계에서 힘 = 질량 × 가속도를 만족해야 한다. kN과 m을 쓰면 질량 단위는 톤이다. 질량 1 t의 무게가 9.80665 kN이다. 대신 킬로그램을 넣으면 모든 주기가 √1000 ≈ 31.6배 어긋난다. 가장 흔한 동적 모델링 오류이고, 정적해석에서는 전혀 보이지 않는다.
감쇠는 계측된 적이 없다. 여러분의 구조물에서 C를 산출한 실험은 없다. 무엇을 쓰든 표와 판단에서 가져온 모델링 가정이며, 5절은 그것을 쓰는 표준적인 방법이 대부분의 진동수에서 요청한 비율을 주지 않음을 보인다.
지반운동은 힘이 아니다. 계측 가속도 기록은 모든 질량에 작용하는 유효력 −M a_g(t)로 들어오고, pattern('UniformExcitation', ...)이 그것을 구성해 준다. 가속도 기록을 절점하중으로 거는 것은 범주 오류이며 그럴듯해 보이는 쓰레기를 만든다.
2. 질량: 집중인가 일관인가, 그리고 얼마나 중요한가
OpenSees는 두 경로를 준다. mass(nodeTag, ...)는 절점에 질량을 직접 준다(집중질량). 보–기둥 요소는 '-mass', 단위길이당질량도 받고, '-cMass'를 붙이면 강성과 같은 형상함수에서 유도한 일관질량행렬을 쓴다.
# 단위: kN, m, ton — 4 m 캔틸레버, IPE 400, 강재 7.85 t/m3 m_bar = 7.85 * 8.45e-3 # 0.0663325 t/m # 집중질량 ops.element('elasticBeamColumn', 1, 1, 2, A, E, Iz, 1, '-mass', m_bar) # 일관질량 ops.element('elasticBeamColumn', 1, 1, 2, A, E, Iz, 1, '-mass', m_bar, '-cMass')
등단면 캔틸레버의 정확 고유진동수는 알려져 있다. ω_n = (β_n L)² √(EI / (m̄ L⁴)), β₁L = 1.87510, β₂L = 4.69409, β₃L = 7.85476. 이 단면에서는 T₁ = 0.0342381 s다. 메시를 늘려가며 OpenSees와 비교하면 이렇다.
요소 수1차, 집중1차, 일관2차, 집중2차, 일관
210.2%0.048%26.2%0.85%
42.79%0.0033%8.82%0.12%
80.71%2.1 × 10⁻⁴ %2.42%0.0080%
160.18%1.3 × 10⁻⁵ %0.62%5.1 × 10⁻⁴ %
320.045%8.0 × 10⁻⁷ %0.16%3.2 × 10⁻⁵ %
일관질량은 요소 2개만으로 기본주기를 0.05% 이내로 준다. 집중질량 2개는 10% 작다. 규칙적인 라멘의 기본주기만 필요하다면 부재당 4~8개 요소의 집중질량으로 충분하다. 그러나 고차모드가 중요하거나 계측 주기와 비교한다면 질량 정식화는 기본값으로 흘려보낼 것이 아니라 한 줄 생각할 값어치가 있다.
오차의 방향도 보아 두자. 집중질량은 주기를 작게 본다. 질량 대비 강성을 크게 본다는 뜻이다. 내진 모델에서는 구조물을 스펙트럼의 다른 구간으로 옮기고, 그 이동은 무작위가 아니라 계통적이다.
3. 세 번째 고유치는 세 번째 휨모드가 아니다
사람들이 오후를 통째로 잃는 함정이 여기 있다. 같은 캔틸레버를 요소 32개·일관질량으로 만들고 모드 4개를 요청하면 진동수는 183.5, 1150.1, 1982.4, 3220.2 rad/s다. 정확 휨진동수는 183.5, 1150.1, 3220.2이다. 세 번째 OpenSees 고유치 1982.4는 어느 것과도 맞지 않는다.
고정–자유 봉의 정확한 1차 축방향 진동수는 ω = (π/2)√(EA/(m̄L²)) = 1982.17 rad/s다. OpenSees 값 1982.37은 이를 0.01%로 맞춘다. 잘못된 것은 없다. 기둥은 질량을 가진 축방향 자유도를 가지므로 축방향 모드가 존재하고, 그것이 진동수 순서로 휨모드 사이에 끼어든다. eigen()은 고유치를 오름차순으로 돌려줄 뿐 "세 번째 휨모드"라는 개념이 없다.
lam = ops.eigen('-fullGenLapack', 4) for m in range(1, 5): w = math.sqrt(lam[m - 1]) tip = ops.nodeEigenvector(tip_node, m) # [ux, uy, rz] kind = 'lateral' if abs(tip[0]) > abs(tip[1]) else 'axial' print(f"mode {m}: omega = {w:9.3f} T = {2*math.pi/w:.7f} {kind}")
mode 1: omega = 183.515 T = 0.0342381 lateral mode 2: omega = 1150.066 T = 0.0054633 lateral mode 3: omega = 1982.365 T = 0.0031695 axial mode 4: omega = 3220.226 T = 0.0019512 lateral
네 줄이면 모드 번호가 다시는 사람을 속이지 못한다. 실제 건물 모델에서는 같은 문제가 연직 모드, 국부 바닥 모드, 비틀림 모드가 관심 있는 병진 모드 사이에 끼어드는 형태로 나타난다. 모드형상을 읽거나 modalProperties로 유효질량비를 확인하는 것은 선택이 아니라, 숫자의 의미를 알아내는 방법이다.
4. 믿기 전에 검증한다: 자유진동
가장 값싼 동적 벤치마크는 초기변위에서 놓아준 1자유도 진동자다. 답이 공식이기 때문이다. T = 0.5 s, m = 1 t, k = ω² m, ζ = 5%로 두면
u(t) = u0 · e^(−ζ ω t) · [ cos(ω_d t) + (ζ/√(1−ζ²)) sin(ω_d t) ] ω_d = ω √(1 − ζ²) 감쇠 고유진동수 T_d = 2π/ω_d = 0.5006262 s
초기조건을 OpenSees에 넣는 방법은 외워둘 만한 관용구다. 정적으로 밀고, 하중을 시간 0에서 고정하고, 패턴을 제거한 뒤 동적해석으로 전환한다.
# 단위: kN, m, ton ops.model('basic', '-ndm', 1, '-ndf', 1) ops.node(1, 0.0); ops.node(2, 0.0); ops.fix(1, 1) ops.mass(2, 1.0) ops.uniaxialMaterial('Elastic', 1, K) ops.element('zeroLength', 1, 1, 2, '-mat', 1, '-dir', 1) # 1) 초기변위를 정적으로 부과 ops.timeSeries('Linear', 1); ops.pattern('Plain', 1, 1); ops.load(2, K * u0) ops.constraints('Plain'); ops.numberer('Plain'); ops.system('BandGeneral') ops.test('NormDispIncr', 1e-12, 100); ops.algorithm('Linear') ops.integrator('LoadControl', 1.0); ops.analysis('Static') assert ops.analyze(1) == 0 # 2) 변형을 유지한 채 하중 제거, 시간 초기화 ops.loadConst('-time', 0.0) ops.remove('loadPattern', 1) ops.wipeAnalysis() # 3) 자유진동 ops.rayleigh(2 * zeta * w_n, 0.0, 0.0, 0.0) # 질량비례만 ops.constraints('Plain'); ops.numberer('Plain'); ops.system('BandGeneral') ops.test('NormDispIncr', 1e-12, 200); ops.algorithm('Linear') ops.integrator('Newmark', 0.5, 0.25) ops.analysis('Transient') for _ in range(n_steps): assert ops.analyze(1, dt) == 0
이 벤치마크를 저장소에 넣어둘 이유가 둘이다. 질량·감쇠·적분기를 공식 하나에 동시에 대조하므로 어긋나면 원인이 빠르게 좁혀진다. 그리고 일회성 확인이 아니라 수렴 시험이다. 간격을 절반으로 줄이면 오차는 4분의 1이 되어야 하고, 그것이 다음 절의 주제다.
5. Rayleigh 감쇠는 정확히 두 진동수에서만 요청한 값을 준다
rayleigh(a0, a1, a1_init, a1_commit)은 C = a0 M + a1 K를 만든다. 그 결과 감쇠비는 진동수에 의존한다.
ζ(ω) = a0/(2ω) + a1 ω/2
두 진동수와 두 목표 비율을 고르면 계수 둘이 정해진다. 나머지는 따라 나오고, 그것을 고른 사람은 아무도 없다.
import numpy as np w_i, w_j = 183.5145, 3220.2175 # 1차와 3차 모드에 고정 A = np.array([[1/(2*w_i), w_i/2], [1/(2*w_j), w_j/2]]) a0, a1 = np.linalg.solve(A, np.array([0.05, 0.05])) print(a0, a1) # -> 17.362 2.938e-05 ops.rayleigh(a0, a1, 0.0, 0.0)
모드ω (rad/s)목표실제
1 (고정점)183.55%5.00%
21150.15%2.44%
3 (고정점)3220.25%5.00%
46310.35%9.41%
두 고정점 사이에서 곡선은 내려앉는다. 2차 모드는 의도한 감쇠의 절반도 못 받아 의도보다 오래 울린다. 위쪽 고정점을 넘어서면 한없이 올라가는데, 가짜 고주파 응답을 억제하려고 일부러 이용하기도 한다. 다만 물려받는 것이 아니라 알고 하는 선택이어야 한다.
몸에 익힐 결론이 셋이다.
고정점 선택은 결과를 바꾸는 모델링 결정이다. 1·3차 대신 1·2차에 고정하면 a1이 달라지고 응답도 달라지는데, 소프트웨어는 아무 경고도 하지 않는다.
강성비례 감쇠는 지정한 강성을 쓴다. 마지막 두 인수가 초기·현재·확정 강성을 고른다. 강성이 열화하는 비선형 모델에서 현재강성 감쇠는 구조물이 물러지면서 함께 줄지만, 초기강성 감쇠는 줄지 않고 항복한 요소에서 큰 가짜 감쇠력을 만들 수 있다.
모드형상을 알고 있다면 modalDamping이 모드별 비율을 직접 준다. 이 문제 전체를 피하지만, 고유치해석이 필요하고 추출한 모드에 대해서만 정의된다는 대가가 있다.
6. 시간적분기, 그리고 확인할 수 있는 오차 법칙
Newmark 법은 매개변수 두 개를 가진다. γ = 1/2가 2차 정확도를 주고, β가 변형을 고른다. β = 1/4는 평균가속도법으로 무조건 안정하다. β = 1/6은 선형가속도법으로 더 정확하지만 조건부 안정이다.
비감쇠 진동자에 γ = 1/2이면 수치 주기가 닫힌 관계를 따른다.
cos(Ω̄ Δt) = 1 − (Ω²Δt²/2) / (1 + β Ω²Δt²) 주기 연장 = T̄/T − 1 = ΩΔt / arccos(...) − 1 안정 조건은 |cos(Ω̄Δt)| ≤ 1 이며, β = 1/6 에서 Δt/T ≤ √12/(2π) = 0.5513
Δt / Tβ = 1/4 측정β = 1/4 정확식β = 1/6 측정β = 1/6 정확식
0.02+0.131%+0.132%+0.066%+0.066%
0.05+0.816%+0.817%+0.407%+0.408%
0.10+3.195%+3.208%+1.595%+1.600%
0.20+11.97%+12.00%+5.818%+5.915%
0.30+24.66%+24.70%+11.72%+11.74%
모든 측정이 법칙의 0.1%p 이내에 들어온다. 적분기에 대한 진짜 검증이며, "충분히 작은 시간간격을 쓰라"는 막연한 지시를 산술로 바꿔준다. 주기를 1% 정확도로 원한다면 관심 있는 최고차 모드에 대해 β = 1/4에서 Δt/T ≤ 0.055가 필요하다.
안정 한계도 똑같이 구체적이다. 선형가속도법을 훑으면 Δt/T = 0.55에서 응답이 유계이고 Δt/T = 0.56에서 초기변위의 8 × 10⁴배로 발산한다. 예측한 한계 0.5513이 그 사이에 정확히 놓인다. 무조건 안정성이 β = 1/4를 상식적 기본값으로 만드는 이유가 이것이다. 모드가 많은 모델에서 조건부 안정 방법의 한계를 정하는 것은 존재하는 최고 진동수이고, 그 진동수는 대개 관심 대상보다 훨씬 높다.
7. 수치감쇠는 기능이고, 켜져 있는지 알아야 한다
평균가속도법에는 수치감쇠가 전혀 없다. 시험한 모든 간격에서 10 사이클에 걸친 사이클당 진폭비가 1.0의 0.3% 이내에 머문다. α = 0.9인 HHT 법은 의도적으로 에너지를 제거한다.
Δt / TNewmark β = 1/4Newmark β = 1/6HHT α = 0.9
0.021.0000011.0000010.99988
0.100.999801.000220.98694
0.200.998311.000580.93263
0.300.997320.998430.86932
이것이 거래다. HHT의 소산은 고주파에 집중되므로, 고주파 수치잡음이 수렴을 막는 비선형 모델에서 인기가 있다. 그러나 같은 메커니즘이 간격이 성기면 실제 응답도 제거한다. 결과와 함께 α를 보고하는 것은 잔소리가 아니다. Δt/T = 0.2에서 α = 0.9의 HHT는 적분되는 모드에 등가 점성감쇠 약 1%를 조용히 더하고 있다.
8. 지반운동 입력, 전달함수와 대조해 검증하기
가속도 기록은 Path 시간이력과 UniformExcitation 패턴으로 들어온다. 패턴은 지정한 방향의 모든 자유도에 −M a_g(t)를 걸고, 해석은 지반에 대한 상대변위를 푼다.
# 단위: kN, m, ton, s ops.timeSeries('Path', 1, '-dt', dt_record, '-filePath', 'record.txt', '-factor', 9.80665) # 파일이 g 단위인 경우 ops.pattern('UniformExcitation', 1, 1, '-accel', 1) # dir 1 = x # 합성 기록을 코드 안에서 줄 때: ops.timeSeries('Path', 1, '-dt', dt, '-values', *values)
이것이 교과서대로 동작하는지 확인하려면 같은 진동자에 조화 지반가속도 a_g = A sin(Ωt)를 건다. 정상상태 상대변위 진폭은 (A/ω²)·Rd, Rd = 1/√((1−r²)² + (2ζr)²), r = Ω/ω다.
r = Ω/ωOpenSees 진폭 (m)닫힌해차이
0.250.0067520.006752< 0.001%
0.900.0301250.0301210.013%
1.000.0633240.0633260.002%
1.100.0267070.0267120.021%
2.000.0021060.0021060.005%
공진을 포함한 전 구간에서 0.03%보다 잘 맞고, ζ = 5%가 예상대로 1/(2ζ) = 10배의 최대 증폭을 준다. 이 확인에서 가져갈 세부가 둘이다. 기록의 dt와 해석의 dt는 다른 것이다. OpenSees가 시간이력을 보간하므로 기록의 표본 간격보다 촘촘하게 해석할 수 있고 대개 그래야 한다. 그리고 기록의 부호와 배율이 중요하다. g 단위 파일은 미터 기반 모델에서 9.80665 배율이 필요하고, 이를 잊으면 구조물이 대략 열 배쯤 얌전해진다.
9. 시간간격을 구체적으로 고르기
네 가지 제약이 동시에 작용하고, 가장 작은 것이 이긴다.
제약요구근거
관심 모드의 정확도주기오차 1%면 Δt ≤ 0.05 T_min6절의 Newmark 법칙
입력 기록의 해상도Δt ≤ 기록의 표본 간격그렇지 않으면 입력이 앨리어싱된다
조건부 안정 적분기의 안정성β = 1/6 이면 Δt ≤ 0.551 T_최고6절. β = 1/4 로 제거 가능
비선형 반복의 수렴상태 변화가 완만할 만큼 작게3부. 항복 사건에 해상도가 필요하다
실무적으로는 Δt와 Δt/2로 각각 돌려 실제로 보고할 응답량을 비교한다. 허용 오차보다 크게 다르면 간격이 컸던 것이다. 이 시험은 실행 한 번을 더 쓸 뿐이고, 더 촘촘한 간격에서 재현되지 않는 숫자를 변호하는 것보다 싸다.
10. 동적 실패와 각각의 의미
증상유력한 원인확인
모든 주기가 약 31.6배 어긋남kN–m 모델에 kg 질량질량 1단위 무게가 9.80665 힘단위인지 확인
고유치해석 실패 또는 음수 반환강성은 있고 질량이 없는 절점, 또는 기구모든 자유 자유도에 질량을 주거나 구속
"3차 모드"가 3차 모드처럼 거동하지 않음축방향·연직·국부 모드가 끼어듦nodeEigenvector 읽기, modalProperties 사용
응답이 한없이 커짐조건부 안정 적분기가 한계를 넘음Newmark(0.5, 0.25) 로 전환
주기가 계통적으로 몇 % 길다시간간격이 성김Newmark 법칙과 대조, Δt 를 절반으로
감쇠비가 시사하는 것보다 빨리 감쇠HHT 등 α 계열의 수치감쇠Newmark(0.5, 0.25) 로 재실행해 비교
고차모드가 지나치게 오래 울림고정점 사이의 Rayleigh 골5절처럼 모든 모드에서 ζ(ω) 평가
항복한 요소에 거대한 감쇠력초기강성 Rayleigh 감쇠현재강성 또는 모드감쇠 사용
11. 같은 논리를 다섯 단계 깊이로
입문자는 질량 단위를 맞추고 기본주기를 손 추정치와 대조한다. 초급 실무자는 1자유도 자유진동을 닫힌해와 검증하고 시간간격이 주기의 작은 분수인지 확인한다. 실무 해석자는 모드 번호가 아니라 모드형상을 읽고, 모든 모드에서 Rayleigh 곡선을 평가하며, 보고 전에 시간간격 절반으로 재실행한다. 선임 엔지니어는 어떤 감쇠 모델이 쓰였는지, 어떤 강성에 비례하는지, 그것이 항복과 어떻게 상호작용하는지 안다. 전문가는 적분기의 수치감쇠가 무엇을 제거했는지 알고, 모델이 신뢰할 만한 진동수 구간을 명시하며, 응답량을 간격 민감도와 함께 보고한다.
12. 동적 모델 최소 점검표
이 체계에서 질량 1단위의 무게가 g 힘단위인가? 주석에 손계산으로 한 번 확인한다.
움직일 수 있는 모든 자유 자유도에 질량이 있거나 구속되어 있는가?
기본주기를 손 추정치나 닫힌해 사례와 대조했는가?
모드형상을 읽어서 모드 번호가 생각한 의미를 가지는지 확인했는가?
질량 정식화(집중/일관)가 기본값이 아니라 결정인가?
관심 있는 각 모드에서 모델이 실제로 적용하는 감쇠비는 얼마인가?
강성비례 항이 어떤 강성을 쓰고 있으며, 항복하는 모델에 그것이 맞는가?
적분기가 무조건 안정인가, 아니면 안정 한계를 확인했는가?
시간간격을 절반으로 줄이면 보고하는 값이 허용 오차보다 크게 변하는가?
지반운동이 모델 단위로 스케일되었고, 하중이 아니라 가진으로 걸렸으며, 보고하는 변위가 상대인지 절대인지 알고 있는가?
이 시리즈의 마지막 글은 모델링에서 물러나 라이브러리 자체로 들어간다. OpenSees가 C++ 클래스로 어떻게 조직되어 있는지, 문서가 답하지 않는 질문을 소스에서 어떻게 확인하는지, 어떻게 확장하는지, 그리고 지금까지의 모든 것을 재현 가능한 엔지니어링 워크플로로 어떻게 묶는지가 주제다.
OpenSees 시리즈 전체
각 편은 닫힌해·독립적인 풀이·OpenSees 소스 중 하나와 대조해 검증했다. 순서대로 읽도록 썼지만 각 편이 자기 전제를 스스로 밝힌다.
1부 — 도메인 모델과 해석 조립
2부 — 단면·기하변환·분포하중
3부 — 파이버 단면·모멘트–곡률·푸시오버
4부 — 질량·감쇠·시간적분 — 지금 보는 글
5부 — 라이브러리 읽기와 재현 가능한 워크플로
6부 — 철근콘크리트 파이버 단면과 구속
7부 — 실제 지진기록·층간변위·증분동적해석
8부 — 3차원: 강막·비틀림·leaning column
9부 — 수렴하지 않을 때: 실패·알고리즘·한계점
10부 — Tcl 읽기와 공개 스크립트 이식
11부 — 쉘·솔리드·지반: 락킹·메시·부지응답
12부 — 후처리: recorder·질의, 그리고 그림이 증명하는 것
13부 — 좌굴과 한계점: 분기점·스냅백·호장법
14부 — Windows: 설치·파일 형식·조용한 실패
15부 — 검증된 정답이 딸린 연습문제와 한영 용어집
16부 — 어떻게 동작하는가: 시행상태·확정상태·해석 루프
17부 — 커뮤니티가 말하는 것, 측정해보면
18부 — 절점 변위에서 파이버 응력까지
19부 — 면진과 감쇠: 속도 의존 요소와 베어링
참고 자료
OpenSeesPy, mass, eigen — 질량 배정과 고유치 추출.
OpenSeesPy, nodeEigenvector, modalProperties — 모드형상과 유효질량 읽기.
OpenSeesPy, rayleigh, modalDamping — 두 가지 감쇠 경로.
OpenSeesPy, Newmark, HHT, CentralDifference — 동적 적분기.
OpenSeesPy, UniformExcitation 패턴, Path 시간이력 — 지반운동 입력.
Hilber, H. M., Hughes, T. J. R., Taylor, R. L., Improved numerical dissipation for time integration algorithms in structural dynamics, Earthquake Engineering & Structural Dynamics 5(3), 1977, doi:10.1002/eqe.4290050306.
Chopra, A. K., Dynamics of Structures: Theory and Applications to Earthquake Engineering — 위에서 재현한 주기연장·진폭감소 거동의 표준 참고서.
Scott, M. H., OpenSees Digital — 감쇠·적분·고유치 함정을 다루는 OpenSees 개발자 블로그.
Pacific Earthquake Engineering Research Center, PEER Strong Ground Motion Databases — 계측 가속도 기록.
Pacific Earthquake Engineering Research Center, OpenSees Wiki.
자료 확인 2026-08-30. 이 글의 모든 수치는 OpenSeesPy 3.8.0에서 생성되었으며 위의 완전한 스크립트로 재현할 수 있다. 프레임워크의 동작을 보여주는 것이지 프로젝트별 해석이나 기준 적합성 검토를 대신하지 않는다.