Torsion | Strength of Materials with Python | Skill-Lync Resources

50% OFF - Ends Soon!

Lesson 8 of 13 25 min

Torsion

When you twist a shaft, shear stresses develop throughout the cross-section. Understanding torsion is essential for designing drive shafts, axles, and rotating machinery components.

The Torsion Formula

For circular shafts under pure torsion:

$$\tau = \frac{T \cdot r}{J}$$

Sponsored

Get an IIT Jammu PG certification

Recognized by Mahindra, Bosch, TATA ELXSI & 500+ companies

See Program Details

Where:

  • $\tau$ = Shear stress (Pa)
  • $T$ = Applied torque (N·m)
  • $r$ = Radial distance from center (m)
  • $J$ = Polar moment of inertia (m⁴)
Maximum shear stress occurs at the outer surface:

$$\tau_{max} = \frac{T \cdot c}{J} = \frac{T}{Z_p}$$

Where $c$ is the outer radius and $Z_p = J/c$ is the polar section modulus.

Sponsored

70% of India's auto industry trusts Skill-Lync

For training their engineers in CAD, CAE & simulation

Learn More

Polar Moment of Inertia

import numpy as np
import matplotlib.pyplot as plt

def solid_shaft(d):
    """
    Properties of solid circular shaft.

    Parameters:
    -----------
    d : float - Diameter (mm)

    Returns:
    --------
    dict with J, Zp, and other properties
    """
    r = d / 2
    J = np.pi * d**4 / 32
    Zp = J / r

    return {
        'd_mm': d,
        'J_mm4': J,
        'Zp_mm3': Zp,
        'area_mm2': np.pi * r**2,
        'type': 'solid'
    }

def hollow_shaft(d_outer, d_inner):
    """
    Properties of hollow circular shaft.
    """
    J = np.pi * (d_outer**4 - d_inner**4) / 32
    Zp = J / (d_outer / 2)

    return {
        'd_outer_mm': d_outer,
        'd_inner_mm': d_inner,
        'J_mm4': J,
        'Zp_mm3': Zp,
        'area_mm2': np.pi * (d_outer**2 - d_inner**2) / 4,
        'ratio': d_inner / d_outer,
        'type': 'hollow'
    }

# Compare solid vs hollow shafts
print("Shaft Comparison: Same Outer Diameter")
print("=" * 50)

d_outer = 60  # mm

solid = solid_shaft(d_outer)
print(f"\nSolid shaft (Ø{d_outer} mm):")
print(f"  J = {solid['J_mm4']:.2e} mm⁴")
print(f"  Zp = {solid['Zp_mm3']:.2e} mm³")
print(f"  Area = {solid['area_mm2']:.1f} mm²")

for ratio in [0.5, 0.7, 0.8]:
    d_inner = d_outer * ratio
    hollow = hollow_shaft(d_outer, d_inner)
    print(f"\nHollow shaft (Ø{d_outer}/Ø{d_inner:.0f} mm, ratio={ratio}):")
    print(f"  J = {hollow['J_mm4']:.2e} mm⁴ ({hollow['J_mm4']/solid['J_mm4']*100:.1f}% of solid)")
    print(f"  Zp = {hollow['Zp_mm3']:.2e} mm³")
    print(f"  Area = {hollow['area_mm2']:.1f} mm² ({hollow['area_mm2']/solid['area_mm2']*100:.1f}% of solid)")

Torsion Analysis

def torsion_analysis(T_Nm, shaft_props, G_GPa):
    """
    Analyze shaft under torsion.

    Parameters:
    -----------
    T_Nm : float - Applied torque in N·m
    shaft_props : dict - From solid_shaft or hollow_shaft
    G_GPa : float - Shear modulus in GPa

    Returns:
    --------
    dict with shear stress and angle of twist per unit length
    """
    T = T_Nm * 1e3  # N·mm
    J = shaft_props['J_mm4']
    G = G_GPa * 1e3  # MPa

    if shaft_props['type'] == 'solid':
        c = shaft_props['d_mm'] / 2
    else:
        c = shaft_props['d_outer_mm'] / 2

    # Maximum shear stress
    tau_max = T * c / J  # MPa

    # Angle of twist per unit length
    theta_per_mm = T / (G * J)  # rad/mm

    return {
        'tau_max_MPa': tau_max,
        'theta_per_m_deg': np.degrees(theta_per_mm * 1000),
        'Zp': shaft_props['Zp_mm3']
    }

# Example: Motor shaft transmitting 50 kW at 1500 RPM
power_kW = 50
rpm = 1500

# Torque from power
T = (power_kW * 1000 * 60) / (2 * np.pi * rpm)  # N·m
print(f"Power: {power_kW} kW at {rpm} RPM")
print(f"Torque: {T:.2f} N·m")

shaft = solid_shaft(50)  # 50mm diameter
G = 80  # GPa for steel

result = torsion_analysis(T, shaft, G)
print(f"\nShaft Analysis (Ø50 mm solid steel):")
print(f"  Max shear stress: {result['tau_max_MPa']:.2f} MPa")
print(f"  Angle of twist: {result['theta_per_m_deg']:.4f}°/m")

Angle of Twist

The total angle of twist over length L:

$$\phi = \frac{TL}{GJ}$$

def angle_of_twist(T_Nm, L_mm, J_mm4, G_GPa):
    """Calculate total angle of twist."""
    T = T_Nm * 1e3  # N·mm
    G = G_GPa * 1e3  # MPa

    phi_rad = T * L_mm / (G * J_mm4)
    phi_deg = np.degrees(phi_rad)

    return phi_deg

# Example
shaft = solid_shaft(40)
phi = angle_of_twist(T_Nm=500, L_mm=2000, J_mm4=shaft['J_mm4'], G_GPa=80)
print(f"Total twist over 2m: {phi:.3f}°")
🎯 3,000+ Engineers Placed
Sponsored
Harshal Sukenkar

Harshal

Fiat Chrysler

Abhishek

Abhishek

TATA ELXSI

Srinithin

Srinithin

Xitadel

Ranjith

Ranjith

Core Automotive

Gaurav Jadhav

Gaurav

Automotive Company

Bino K Biju

Bino

Design Firm

Aseem Shrivastava

Aseem

EV Company

Puneet

Puneet

Automotive Company

Vishal Kumar

Vishal

EV Startup

Power Transmission

Power transmitted by a rotating shaft:

Sponsored

3,000+ engineers placed at top companies in 2024

Mahindra, Bosch, TATA ELXSI, Capgemini and more

See Placement Stats

$$P = T \cdot \omega = \frac{2\pi n T}{60}$$

Where:

  • $P$ = Power (W)
  • $T$ = Torque (N·m)
  • $\omega$ = Angular velocity (rad/s)
  • $n$ = Rotational speed (RPM)
def power_transmission(T_Nm=None, P_kW=None, rpm=None):
    """
    Power-torque-RPM relationship.
    Provide any two to calculate the third.
    """
    if T_Nm is not None and rpm is not None:
        # Calculate power
        P = 2 * np.pi * rpm * T_Nm / 60
        return {'P_kW': P / 1000, 'T_Nm': T_Nm, 'rpm': rpm}

    elif P_kW is not None and rpm is not None:
        # Calculate torque
        T = P_kW * 1000 * 60 / (2 * np.pi * rpm)
        return {'P_kW': P_kW, 'T_Nm': T, 'rpm': rpm}

    elif P_kW is not None and T_Nm is not None:
        # Calculate RPM
        n = P_kW * 1000 * 60 / (2 * np.pi * T_Nm)
        return {'P_kW': P_kW, 'T_Nm': T_Nm, 'rpm': n}

# Examples
print("Power Transmission Examples:")
print("-" * 40)

# Example 1: Electric motor
result = power_transmission(P_kW=75, rpm=1450)
print(f"75 kW motor at 1450 RPM:")
print(f"  Torque = {result['T_Nm']:.2f} N·m")

# Example 2: Known torque
result = power_transmission(T_Nm=200, rpm=3000)
print(f"\n200 N·m at 3000 RPM:")
print(f"  Power = {result['P_kW']:.2f} kW")

Shaft Design

def design_shaft(P_kW, rpm, tau_allow_MPa, G_GPa, phi_allow_deg_per_m=0.25,
                 shaft_type='solid', hollow_ratio=0.6):
    """
    Design a shaft for given power transmission.

    Parameters:
    -----------
    P_kW : float - Power to transmit
    rpm : float - Rotational speed
    tau_allow_MPa : float - Allowable shear stress
    G_GPa : float - Shear modulus
    phi_allow_deg_per_m : float - Allowable angle of twist per meter
    shaft_type : str - 'solid' or 'hollow'
    hollow_ratio : float - d_inner/d_outer for hollow shaft
    """
    # Calculate required torque
    T = P_kW * 1000 * 60 / (2 * np.pi * rpm)  # N·m
    T_mm = T * 1000  # N·mm

    print(f"Shaft Design for {P_kW} kW at {rpm} RPM")
    print(f"Required torque: {T:.2f} N·m")
    print("=" * 50)

    # Design based on strength (shear stress)
    Zp_required = T_mm / tau_allow_MPa  # mm³

    if shaft_type == 'solid':
        # Zp = πd³/16
        d_strength = (16 * Zp_required / np.pi) ** (1/3)
    else:
        # Zp = πd³(1-k⁴)/(16) where k = d_inner/d_outer
        k = hollow_ratio
        d_strength = (16 * Zp_required / (np.pi * (1 - k**4))) ** (1/3)

    # Design based on stiffness (angle of twist)
    G = G_GPa * 1e3  # MPa
    phi_allow_rad = np.radians(phi_allow_deg_per_m) / 1000  # rad/mm
    J_required = T_mm / (G * phi_allow_rad)  # mm⁴

    if shaft_type == 'solid':
        # J = πd⁴/32
        d_stiffness = (32 * J_required / np.pi) ** (1/4)
    else:
        # J = πd⁴(1-k⁴)/32
        d_stiffness = (32 * J_required / (np.pi * (1 - k**4))) ** (1/4)

    # Governing diameter
    d_required = max(d_strength, d_stiffness)

    # Round up to standard size
    standard_sizes = [20, 25, 30, 35, 40, 45, 50, 55, 60, 65, 70, 75, 80, 90, 100, 110, 120]
    d_selected = next((s for s in standard_sizes if s >= d_required), standard_sizes[-1])

    print(f"\n{shaft_type.upper()} SHAFT:")
    print(f"  Based on strength (τ ≤ {tau_allow_MPa} MPa): d ≥ {d_strength:.1f} mm")
    print(f"  Based on stiffness (φ ≤ {phi_allow_deg_per_m}°/m): d ≥ {d_stiffness:.1f} mm")
    print(f"  Required diameter: {d_required:.1f} mm")
    print(f"  Selected standard: {d_selected} mm")

    # Verify design
    if shaft_type == 'solid':
        shaft = solid_shaft(d_selected)
    else:
        shaft = hollow_shaft(d_selected, d_selected * hollow_ratio)

    actual = torsion_analysis(T, shaft, G_GPa)
    print(f"\nVerification with Ø{d_selected} mm:")
    print(f"  Actual τmax: {actual['tau_max_MPa']:.2f} MPa (limit: {tau_allow_MPa})")
    print(f"  Actual φ: {actual['theta_per_m_deg']:.4f}°/m (limit: {phi_allow_deg_per_m})")

    if shaft_type == 'hollow':
        print(f"  Inner diameter: {d_selected * hollow_ratio:.0f} mm")
        print(f"  Weight savings: {(1 - shaft['area_mm2']/(np.pi*(d_selected/2)**2))*100:.1f}%")

    return d_selected

# Design example
print("\n" + "="*60)
d_solid = design_shaft(
    P_kW=100,
    rpm=1500,
    tau_allow_MPa=50,
    G_GPa=80,
    shaft_type='solid'
)

print("\n" + "="*60)
d_hollow = design_shaft(
    P_kW=100,
    rpm=1500,
    tau_allow_MPa=50,
    G_GPa=80,
    shaft_type='hollow',
    hollow_ratio=0.6
)

Shear Stress Distribution

def visualize_torsion_stress(d_outer, d_inner=0, T_Nm=100):
    """Visualize shear stress distribution in a shaft."""

    if d_inner == 0:
        shaft = solid_shaft(d_outer)
        r = np.linspace(0, d_outer/2, 50)
    else:
        shaft = hollow_shaft(d_outer, d_inner)
        r = np.linspace(d_inner/2, d_outer/2, 50)

    J = shaft['J_mm4']
    T = T_Nm * 1e3  # N·mm

    # Shear stress at each radius
    tau = T * r / J

    # Create visualization
    fig, axes = plt.subplots(1, 2, figsize=(12, 5))

    # 1. Cross-section with stress indication
    ax1 = axes[0]
    theta = np.linspace(0, 2*np.pi, 100)

    # Outer circle
    x_out = (d_outer/2) * np.cos(theta)
    y_out = (d_outer/2) * np.sin(theta)
    ax1.plot(x_out, y_out, 'b-', lw=2)

    # Inner circle (if hollow)
    if d_inner > 0:
        x_in = (d_inner/2) * np.cos(theta)
        y_in = (d_inner/2) * np.sin(theta)
        ax1.plot(x_in, y_in, 'b-', lw=2)
        ax1.fill(x_in, y_in, color='white')

    # Stress arrows (tangential)
    for ri in [d_outer/4, d_outer/2] if d_inner == 0 else [d_inner/2*1.2, (d_inner/2+d_outer/2)/2, d_outer/2*0.9]:
        for angle in [0, np.pi/2, np.pi, 3*np.pi/2]:
            x = ri * np.cos(angle)
            y = ri * np.sin(angle)
            # Tangent direction (perpendicular to radius)
            dx = -np.sin(angle) * 5
            dy = np.cos(angle) * 5
            ax1.annotate('', xy=(x+dx, y+dy), xytext=(x, y),
                        arrowprops=dict(arrowstyle='->', color='red', lw=1.5))

    ax1.set_xlim(-d_outer*0.7, d_outer*0.7)
    ax1.set_ylim(-d_outer*0.7, d_outer*0.7)
    ax1.set_aspect('equal')
    ax1.set_title('Cross-Section with Shear Stress\n(tangential direction)')
    ax1.grid(True, alpha=0.3)

    # 2. Stress distribution
    ax2 = axes[1]
    ax2.fill_between(r, 0, tau, alpha=0.3, color='red')
    ax2.plot(r, tau, 'r-', lw=2)

    ax2.set_xlabel('Radius (mm)', fontsize=11)
    ax2.set_ylabel('Shear Stress τ (MPa)', fontsize=11)
    ax2.set_title('Radial Stress Distribution')
    ax2.grid(True, alpha=0.3)

    # Annotations
    ax2.annotate(f'τmax = {max(tau):.1f} MPa',
                xy=(r[-1], tau[-1]), xytext=(r[-1]-5, tau[-1]+2),
                fontsize=10, fontweight='bold')

    if d_inner > 0:
        ax2.annotate(f'τmin = {min(tau):.1f} MPa',
                    xy=(r[0], tau[0]), xytext=(r[0]+2, tau[0]+2),
                    fontsize=10)

    plt.tight_layout()
    plt.show()

# Visualize
print("Solid shaft:")
visualize_torsion_stress(d_outer=60, T_Nm=500)

print("\nHollow shaft:")
visualize_torsion_stress(d_outer=60, d_inner=40, T_Nm=500)

Key Takeaways

  • Torsion formula: $\tau = Tr/J$ — stress varies linearly with radius
  • Hollow shafts are more efficient — material at center contributes little
  • Angle of twist: $\phi = TL/(GJ)$
  • Power-torque relationship: $P = 2\pi n T / 60$
  • Design by both strength (stress limit) and stiffness (twist limit)

Next lesson: We'll explore combined loading and failure theories.

3,000+ Engineers Placed in Top Companies
Career Growth

3,000+ Engineers Placed in Top Companies

Join the ranks of successful engineers at Bosch, Tata, L&T, and 500+ hiring partners.