Strasmore Research
การเรียนรู้ Matt Connorโดย Matt Connor · อัปเดตเมื่อ 2026-07-24

วิธีคำนวณผลตอบแทนหุ้นรายเดือน

ทำความเข้าใจวิธีการคำนวณผลตอบแทนหุ้นรายเดือน ทั้งการใช้ราคาปิด การรวมเงินปันผล และการปรับราคาจากการแตกหุ้น เพื่อให้เข้าใจความแตกต่างของข้อมูลราคา

หากถามว่าหุ้นตัวหนึ่งมีผลตอบแทนอย่างไรในเดือนมิถุนายน คุณอาจได้รับตัวเลขที่แตกต่างกันจากแหล่งข้อมูลต่างๆ ซึ่งตัวเลขเหล่านั้นถูกต้องทั้งหมด ผลตอบแทนรายเดือนของหุ้นถูกกำหนดโดยปัจจัยที่คนส่วนใหญ่ไม่ทราบ ได้แก่ ราคาใดสองราคาที่ใช้กำหนดจุดเริ่มต้นและจุดสิ้นสุดของเดือน มีการรวมเงินปันผลหรือไม่ และ มีการปรับราคา (adjusted) เพื่อรองรับการแตกหุ้นหรือไม่ หน้าเว็บนี้จะนำวิธีการคำนวณที่แตกต่างกันมาเปรียบเทียบกันโดยใช้ข้อมูลราคาจริง เพื่อให้คุณเข้าใจถึงสาเหตุของความแตกต่างเหล่านั้นอย่างชัดเจน

Close-to-close: มาตรฐานที่ใช้กันทั่วไป

เกณฑ์ที่ผู้ให้บริการดัชนี, เอกสารข้อมูลกองทุน (fund fact sheets) และหน้าแสดงราคาโดยทั่วไปใช้ คือ ผลตอบแทนรายเดือนจะคำนวณตั้งแต่ ราคาปิดของเซสชันปกติสุดท้ายของเดือนก่อนหน้า ไปจนถึง ราคาปิดสุดท้ายของเดือนนี้ โดยราคาปิดสุดท้ายของเดือนพฤษภาคมจะเป็นจุดเริ่มต้นของเดือนมิถุนายน การคำนวณนั้นเรียบง่าย คือ นำราคาปิดลบด้วยราคาเริ่มต้น แล้วหารด้วยราคาเริ่มต้น ตัวอย่างเบื้องต้น: หุ้นที่ปิดเดือนพฤษภาคมที่ $50.00 และปิดเดือนมิถุนายนที่ $53.50 จะมีผลตอบแทนคือ (53.50 − 50.00) ÷ 50.00 = 0.07 หรือ 7% สำหรับเดือนนั้น ทุกเกณฑ์ที่ระบุในหน้านี้ใช้ข้อมูลนำเข้าที่แตกต่างกันเข้าสู่สูตรเดียวกัน ต่อไปนี้คือข้อมูลจริงของเดือนมิถุนายน 2026 เปรียบเทียบกับเกณฑ์ทางเลือกหลัก:

คำสั่งดึงข้อมูลการวัดผลเดือนมิถุนายน 2026 — close-to-close เทียบกับ open-to-close สำหรับ NVDA และ SPY
SQL เบื้องหลังตัวเลขแต่ละตัว
SELECT ticker,
       round(argMaxIf(cl, day, day <= '2026-05-31'), 2) AS may_final_close,
       round(argMinIf(op, day, day >= '2026-06-01'), 2) AS june_first_open,
       round(argMaxIf(cl, day, day <= '2026-06-30'), 2) AS june_final_close,
       round(100 * (argMaxIf(cl, day, day <= '2026-06-30') - argMaxIf(cl, day, day <= '2026-05-31'))
             / argMaxIf(cl, day, day <= '2026-05-31'), 2) AS close_to_close_pct,
       round(100 * (argMaxIf(cl, day, day <= '2026-06-30') - argMinIf(op, day, day >= '2026-06-01'))
             / argMinIf(op, day, day >= '2026-06-01'), 2) AS open_to_close_pct,
       round(abs(100 * (argMaxIf(cl, day, day <= '2026-06-30') - argMinIf(op, day, day >= '2026-06-01'))
                 / argMinIf(op, day, day >= '2026-06-01')
             - 100 * (argMaxIf(cl, day, day <= '2026-06-30') - argMaxIf(cl, day, day <= '2026-05-31'))
                 / argMaxIf(cl, day, day <= '2026-05-31')), 2) AS convention_gap_points
FROM (
    SELECT ticker,
               toDate(toTimeZone(window_start, 'America/New_York')) AS day,
               argMinIf(toFloat64(open), window_start, rth) AS op,
               argMaxIf(toFloat64(close), window_start, rth) AS cl
        FROM (
            SELECT ticker, window_start, open, close,
                   toTimeZone(window_start, 'America/New_York') >= toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 09:30:00'), 'America/New_York')
                   AND toTimeZone(window_start, 'America/New_York') < toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 16:00:00'), 'America/New_York') AS rth
            FROM global_markets.delayed_stocks_minute_aggs
            WHERE ticker IN ('NVDA', 'SPY')
              AND window_start >= '2026-05-28 04:00:00'
              AND window_start < '2026-07-01 08:00:00'
        )
        GROUP BY ticker, day
)
GROUP BY ticker
ORDER BY ticker

ผลตอบแทนเดือนมิถุนายนของ NVDA แบบ close-to-close คือ -5.39% แต่แบบ -7.4% วัดจากราคาเปิดของเซสชันปกติแรกของเดือนมิถุนายนไปจนถึงราคาปิดสุดท้าย หุ้นตัวเดิม เดือนเดิม แต่มีส่วนต่างระหว่างคำตอบที่ถูกต้องทั้งสองแบบอยู่ 2.01 percentage points ความแตกต่างทั้งหมดเกิดจากช่วงเวลาข้ามคืนและวันหยุดเพียงช่วงเดียว: NVDA ปิดเดือนพฤษภาคมที่ $211.15 และเปิดเดือนมิถุนายนที่ $215.73 — ส่วนต่างที่เพิ่มขึ้นนี้ถือเป็นส่วนหนึ่งของ "เดือนมิถุนายน" ในเกณฑ์ open-to-close และถือเป็นส่วนต่างที่รอยต่อในเกณฑ์ close-to-close สำหรับ SPY แสดงโครงสร้างแบบเดียวกันในระดับที่น้อยกว่า: -1.33% แบบ close-to-close เทียบกับ -1.2% แบบ open-to-close

ไม่มีตัวเลขใดผิด เกณฑ์ close-to-close ตอบคำถามว่า "ผู้ที่ถือหุ้นต่อเนื่องได้รับผลตอบแทนอย่างไรในช่วงรอยต่อของเดือน?" ส่วนเกณฑ์ open-to-close ตอบคำถามว่า "การซื้อขายภายในเดือนนั้นสร้างผลตอบแทนเท่าใดแก่ผู้ที่ซื้อ ณ ราคาเปิดของเดือนมิถุนายน?" ตัวเลขทั้งสองจะต่างกันเมื่อตลาดเกิดช่องว่างราคา (gap) ข้ามรอยต่อ ซึ่ง ช่องว่างราคาข้ามคืน เป็นเรื่องปกติที่เกิดขึ้นได้ทั่วไป ไม่ใช่เรื่องหายาก

เงินปันผล: ผลตอบแทนจากส่วนต่างราคา เทียบกับ ผลตอบแทนรวม

ทางเลือกที่สองคือ เงินสดที่หุ้นจ่ายออกมาในระหว่างเดือนนั้นถูกนำมาคำนวณด้วยหรือไม่? price return จะไม่นำมาคำนวณ แต่ total return จะนำเงินส่วนนั้นกลับมาบวกเพิ่ม สำหรับเดือนเดี่ยวๆ ส่วนใหญ่ ความแตกต่างนี้จะมีเพียงเล็กน้อย เนื่องจากผู้จ่ายปันผลรายไตรมาสจะจ่ายเงินประมาณหนึ่งในสี่ของอัตราผลตอบแทนต่อไตรมาส แต่ความแตกต่างนี้จะทวีคูณขึ้นจนกลายเป็นช่องว่างขนาดใหญ่เมื่อเวลาผ่านไปหลายปี และเดือน มิถุนายน 2026 เป็นเดือนที่มีการจ่ายปันผลของ SPY พอดี:

คำสั่งดึงข้อมูลSPY เดือนมิถุนายน 2026 — price return เทียบกับ total return (รวมมิถุนายน ex-dividend)
SQL เบื้องหลังตัวเลขแต่ละตัว
WITH px AS (
    SELECT argMaxIf(cl, day, day <= '2026-05-31') AS may_close,
           argMaxIf(cl, day, day <= '2026-06-30') AS jun_close
    FROM (
        SELECT ticker,
               toDate(toTimeZone(window_start, 'America/New_York')) AS day,
               argMinIf(toFloat64(open), window_start, rth) AS op,
               argMaxIf(toFloat64(close), window_start, rth) AS cl
        FROM (
            SELECT ticker, window_start, open, close,
                   toTimeZone(window_start, 'America/New_York') >= toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 09:30:00'), 'America/New_York')
                   AND toTimeZone(window_start, 'America/New_York') < toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 16:00:00'), 'America/New_York') AS rth
            FROM global_markets.delayed_stocks_minute_aggs
            WHERE ticker IN ('NVDA', 'SPY')
              AND window_start >= '2026-05-28 04:00:00'
              AND window_start < '2026-07-01 08:00:00'
        )
        GROUP BY ticker, day
    )
    WHERE ticker = 'SPY'
),
dv AS (
    SELECT sum(cash_amount) AS div_per_share
    FROM global_markets.stocks_dividends
    WHERE ticker = 'SPY'
      AND ex_dividend_date >= '2026-06-01'
      AND ex_dividend_date <= '2026-06-30'
)
SELECT round(may_close, 2) AS may_final_close,
       round(jun_close, 2) AS june_final_close,
       round(div_per_share, 4) AS june_dividend_per_share,
       round(100 * (jun_close - may_close) / may_close, 2) AS price_return_pct,
       round(100 * div_per_share / may_close, 2) AS dividend_contribution_pct,
       round(100 * ((jun_close + div_per_share) - may_close) / may_close, 2) AS total_return_pct
FROM px CROSS JOIN dv

price return ของ SPY ในเดือน มิถุนายน คือ -1.33% เมื่อบวกเงินปันผลจำนวน $1.9035 ต่อหุ้นที่ขึ้นเครื่องหมาย ex-dividend ในระหว่างเดือน จะทำให้ total return เพิ่มขึ้นเป็น -1.08% ซึ่งคิดเป็นสัดส่วนจากเงินสดที่ 0.25% ตระกูลดัชนีมีการเผยแพร่ข้อมูลทั้งสองรูปแบบ (ดัชนี "S&P 500" ที่คุณเห็นมักจะเป็น price index) หน้าแสดงผลการดำเนินงานของกองทุนถูกกำหนดให้ต้องแสดงค่า total return และเครื่องมือคัดกรองหุ้นมีการใช้ทั้งสองค่าผสมกันอย่างอิสระ เมื่อข้อมูลจากสองแหล่งไม่ตรงกันเพียงเล็กน้อยในเดือนที่มีการจ่ายปันผล เงินปันผลคือสาเหตุแรกที่ต้องสงสัย เนื่องจาก วันที่ขึ้นเครื่องหมาย ex-dividend เป็นตัวกำหนดว่าเงินปันผลนั้นจะถูกนับรวมในเดือนใด

ความแตกต่างในเดือน มิถุนายน เพียงเดือนเดียวมีค่าเพียงเศษส่วนของเปอร์เซ็นต์ แต่ระยะเวลาในการถือครองคือสิ่งที่ทำให้การคำนวณทั้งสองแบบแตกต่างกันอย่างชัดเจน ต่อไปนี้คือการคำนวณแบบเดียวกันที่ขยายระยะเวลาออกไปเป็นห้าปี:

คำสั่งดึงข้อมูลSPY ในรอบ 5 ปี ตั้งแต่ มิถุนายน 2021 ถึง มิถุนายน 2026 — price return เทียบกับ return รวมเงินปันผล
SQL เบื้องหลังตัวเลขแต่ละตัว
WITH daily AS (
    SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS day,
           argMaxIf(toFloat64(close), window_start,
               toTimeZone(window_start, 'America/New_York') >= toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 09:30:00'), 'America/New_York')
               AND toTimeZone(window_start, 'America/New_York') < toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 16:00:00'), 'America/New_York')) AS cl
    FROM global_markets.delayed_stocks_minute_aggs
    WHERE ticker = 'SPY'
      AND ((window_start >= '2021-06-28 04:00:00' AND window_start < '2021-07-01 08:00:00')
        OR (window_start >= '2026-06-26 04:00:00' AND window_start < '2026-07-01 08:00:00'))
    GROUP BY day
),
px AS (
    SELECT argMaxIf(cl, day, day <= '2021-06-30') AS start_close,
           argMaxIf(cl, day, day <= '2026-06-30') AS end_close
    FROM daily
),
dv AS (
    SELECT round(sum(cash_amount), 2) AS divs_per_share,
           count() AS payments
    FROM global_markets.stocks_dividends
    WHERE ticker = 'SPY'
      AND ex_dividend_date >= '2021-07-01'
      AND ex_dividend_date <= '2026-06-30'
)
SELECT round(start_close, 2) AS june_2021_close,
       round(end_close, 2) AS june_2026_close,
       divs_per_share AS dividends_paid_per_share,
       payments AS dividend_payments,
       round(100 * (end_close - start_close) / start_close, 2) AS five_year_price_return_pct,
       round(100 * ((end_close + divs_per_share) - start_close) / start_close, 2) AS five_year_return_with_divs_pct,
       round(100 * divs_per_share / start_close, 2) AS dividend_points_added
FROM px CROSS JOIN dv

จากราคาปิดในเดือน มิถุนายน 2021 ที่ $428.07 ไปยังราคาปิดในเดือน มิถุนายน 2026 ที่ $746.32 price return ระยะเวลาห้าปีของ SPY วัดค่าได้ที่ 74.35% ในช่วงเวลาเดียวกันนี้มีการจ่ายเงินปันผลรวม 20 คิดเป็นเงิน $34.07 ต่อหุ้น เมื่อรวมเงินสดดังกล่าวจะทำให้ตัวเลขเพิ่มขึ้นเป็น 82.3% ซึ่งมีส่วนต่างอยู่ 7.96 จุด แม้จะยังไม่มีการนำเงินปันผลแม้แต่ครั้งเดียวไปลงทุนต่อก็ตาม ดัชนีแบบ total-return ที่แท้จริงจะนำเงินปันผลแต่ละครั้งไปลงทุนต่อทันทีในวันที่ขึ้นเครื่องหมาย ex-date และการนำหุ้นที่ได้จากการลงทุนต่อมาคำนวณจะยิ่งทำให้ช่องว่างนี้กว้างขึ้นไปอีก สำหรับหุ้นที่มีการจ่ายปันผลสม่ำเสมอ คำว่า "ส่วนต่างขนาดใหญ่" ไม่ใช่เพียงคำเปรียบเทียบ แต่เป็นผลลัพธ์ปกติที่เกิดจากการได้รับเงินสดรายไตรมาสต่อเนื่องกันหลายปี

ราคาปิดแบบปรับปรุง (Adjusted close) เทียบกับราคาปิดจริง (Raw close): กับดักจากการแตกหุ้น

เครื่องมือทำกราฟส่วนใหญ่ เช่น Yahoo Finance, Google Finance และแอปพลิเคชันของโบรกเกอร์ส่วนใหญ่ จะแสดงค่า adjusted close: ซึ่งเป็นชุดข้อมูลราคาในอดีตที่ผ่านการหารด้วยอัตราส่วนการแตกหุ้น (และในบางแพลตฟอร์มมีการปรับปรุงเรื่องเงินปันผลด้วย) เพื่อให้สามารถเปรียบเทียบราคาผ่านช่วงเวลาต่างๆ ได้ ส่วนคลังข้อมูลของเราจะเก็บข้อมูลราคาตามที่เกิดขึ้นจริงในตลาด ในเดือนปกติ ข้อมูลทั้งสองชุดนี้จะมีค่าตรงกัน แต่ในเดือนที่มีการแตกหุ้น ข้อมูลจะแสดงผลต่างกันอย่างมาก เช่น กรณีที่ NVDA แตกหุ้นในอัตราส่วน 10-for-1 เมื่อวันที่ 10 มิถุนายน 2024 ซึ่งเกิดขึ้นภายในเดือนดังกล่าว:

คำสั่งดึงข้อมูลNVDA เดือนมิถุนายน 2024 — การคำนวณแบบ raw close-to-close เทียบกับ split-adjusted return
SQL เบื้องหลังตัวเลขแต่ละตัว
WITH px AS (
    SELECT argMaxIf(cl, day, day <= '2024-05-31') AS may_close,
           argMaxIf(cl, day, day <= '2024-06-30') AS jun_close
    FROM (
        SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS day,
               argMaxIf(toFloat64(close), window_start,
                   toTimeZone(window_start, 'America/New_York') >= toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 09:30:00'), 'America/New_York')
                   AND toTimeZone(window_start, 'America/New_York') < toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 16:00:00'), 'America/New_York')) AS cl
        FROM global_markets.delayed_stocks_minute_aggs
        WHERE ticker = 'NVDA'
          AND window_start >= '2024-05-29 04:00:00'
          AND window_start < '2024-07-01 08:00:00'
        GROUP BY day
    )
),
sp AS (
    SELECT split_to / split_from AS ratio
    FROM global_markets.stocks_splits
    WHERE ticker = 'NVDA'
      AND execution_date >= '2024-06-01'
      AND execution_date <= '2024-06-30'
)
SELECT round(may_close, 2) AS may_final_close_raw,
       round(jun_close, 2) AS june_final_close_raw,
       toInt32(ratio) AS shares_after_split_per_old_share,
       round(100 * (jun_close - may_close) / may_close, 2) AS raw_price_change_pct,
       round(may_close / ratio, 2) AS may_close_split_adjusted,
       round(100 * (jun_close - may_close / ratio) / (may_close / ratio), 2) AS adjusted_return_pct
FROM px CROSS JOIN sp

หากดูจากราคาจริง NVDA "ลดลง" จาก $1097.46 เหลือ $123.41 ในเดือนมิถุนายนนั้น ซึ่งคิดเป็นการดิ่งลงถึง -88.75% แต่ในความเป็นจริงไม่ได้เกิดเหตุการณ์ดังกล่าวขึ้น ในวันที่เกิดการแตกหุ้น หุ้นเดิมหนึ่งหุ้นจะกลายเป็นหุ้นใหม่ 10 หุ้น และราคาจะถูกหารลงเพื่อให้สอดคล้องกัน ส่งผลให้มูลค่าเงินของผู้ถือหุ้นทุกคนยังคงเท่าเดิม หากนำราคาปิดเดือนพฤษภาคมมาหารด้วยอัตราส่วนเดียวกัน ซึ่งเท่ากับ $109.75 เมื่อปรับปรุงตามการแตกหุ้นแล้ว ราคาในเดือนมิถุนายน 2024 จะวัดค่าได้ที่ 12.45% ซึ่งเป็นเดือนที่ราคาปรับตัวขึ้น แหล่งข้อมูลใดก็ตามที่ใช้ข้อมูลแบบ adjusted จะรายงานค่าที่ใกล้เคียงกับตัวเลขที่สอง ส่วนการคำนวณแบบผิวเผินจากราคาจริงจะรายงานค่าแรก ราคาแบบ adjusted close คือสาเหตุที่พบบ่อยที่สุดที่ทำให้แหล่งข้อมูลสองแห่งรายงานผลตอบแทนรายเดือนในอดีตต่างกันอย่างสิ้นเชิง หากพบว่าตัวเลขมีค่าสูงหรือต่ำผิดปกติ ให้ตรวจสอบ ปฏิทินการแตกหุ้น เป็นอันดับแรก

ราคา "ปิด" ที่แท้จริงคือราคาใด?

ยังมีข้อจำกัดอีกประการหนึ่งที่ซ่อนอยู่ในธรรมเนียมปฏิบัติ นั่นคือราคาปิด ตัวเลขที่ใช้ในเอกสารข้อมูลสำคัญทุกฉบับคือราคาจากการประมูลปิดตลาดอย่างเป็นทางการ ซึ่งเป็นราคาเดียวที่กำหนดโดย การประมูลปิดตลาด เมื่อเวลา 16:00 น. ET อย่างไรก็ตาม การซื้อขายยังคงดำเนินต่อไปในช่วงหลังเวลาทำการ (after hours) และราคาล่าสุดของช่วงเวลาที่ขยายออกไปอาจแตกต่างจากราคาปิดอย่างเป็นทางการ:

คำสั่งดึงข้อมูลSPY ณ 30 มิถุนายน 2026 — official-close เทียบกับ final extended-hours print
SQL เบื้องหลังตัวเลขแต่ละตัว
SELECT round(argMaxIf(toFloat64(close), window_start, rth), 2) AS regular_session_close,
       round(argMax(toFloat64(close), window_start), 2) AS last_extended_print,
       round(100 * (argMax(toFloat64(close), window_start) - argMaxIf(toFloat64(close), window_start, rth))
             / argMaxIf(toFloat64(close), window_start, rth), 3) AS after_hours_drift_pct
FROM (
    SELECT window_start, close,
           toTimeZone(window_start, 'America/New_York') >= toDateTime('2026-06-30 09:30:00', 'America/New_York')
           AND toTimeZone(window_start, 'America/New_York') < toDateTime('2026-06-30 16:00:00', 'America/New_York') AS rth
    FROM global_markets.delayed_stocks_minute_aggs
    WHERE ticker = 'SPY'
      AND window_start >= '2026-06-30 04:00:00'
      AND window_start < '2026-07-01 08:00:00'
)

เมื่อวันที่ 30 มิถุนายน ราคาทั้งสองต่างกันอยู่ -0.003% ซึ่งถือว่าน้อยมากในเย็นวันนั้น แต่ในคืนที่มีการประกาศผลประกอบการของหุ้นรายตัว ช่วงเวลาที่ขยายออกไปอาจทำให้ราคาเคลื่อนไหวในระดับเปอร์เซ็นต์ ซึ่งจะส่งผลให้ผลตอบแทนรายเดือนอย่างเป็นทางการถูกนำไปคำนวณในเดือน ถัดไป การซื้อขายช่วงหลังเวลาทำการและก่อนตลาดเปิด จะอธิบายรายละเอียดเกี่ยวกับข้อจำกัดดังกล่าว กรณีพิเศษที่เกี่ยวข้องอีกประการหนึ่งคือ การสิ้นสุดของเดือนอาจตรงกับวันหยุดซึ่งทำให้เวลาทำการสั้นลง โดยตลาดจะปิดทำการปกติในเวลา 13:00 น. ET และราคาปิดอย่างเป็นทางการจะถูกกำหนดในการประมูลปิดตลาดที่เร็วขึ้น ซึ่งสามารถตรวจสอบได้จาก ตารางวันหยุดตลาด

การคิดผลตอบแทนทบต้นสิบสองเดือนเป็นรายปี

ผลตอบแทนรายปีไม่ใช่ผลรวมของผลตอบแทนรายเดือนทั้งสิบสองเดือน แต่คือผลคูณของผลตอบแทนเหล่านั้น สูตรการคำนวณคือ: เปลี่ยนผลตอบแทนแต่ละเดือนให้เป็นปัจจัยการเติบโต (1 + ผลตอบแทน) จากนั้นนำปัจจัยทั้งสิบสองตัวมาคูณกัน แล้วลบออกด้วย 1 หากเดือนหนึ่งติดลบ 5% และเดือนถัดไปบวก 5% ผลรวมจะเท่ากับศูนย์ แต่หากคิดแบบทบต้นจะได้ 0.95 × 1.05 − 1 = −0.25% ต่อไปนี้คือเส้นทางรายเดือนที่เกิดขึ้นจริงของ SPY ในช่วงสิบสองเดือนที่สิ้นสุดใน มิถุนายน 2026:

คำสั่งดึงข้อมูลSPY monthly close-to-close returns — 12 เดือน สิ้นสุด มิถุนายน 2026 แบบ simple และ log
SQL เบื้องหลังตัวเลขแต่ละตัว
WITH daily AS (
    SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS day,
           argMaxIf(toFloat64(close), window_start,
               toTimeZone(window_start, 'America/New_York') >= toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 09:30:00'), 'America/New_York')
               AND toTimeZone(window_start, 'America/New_York') < toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 16:00:00'), 'America/New_York')) AS cl
    FROM global_markets.delayed_stocks_minute_aggs
    WHERE ticker = 'SPY'
      AND window_start >= '2025-06-24 04:00:00'
      AND window_start < '2026-07-01 08:00:00'
    GROUP BY day
),
monthly AS (
    SELECT toStartOfMonth(day) AS month_start,
           argMax(cl, day) AS month_close
    FROM daily
    GROUP BY month_start
),
rets AS (
    SELECT month_start,
           formatDateTime(month_start, '%Y-%m') AS month,
           round(month_close, 2) AS month_final_close,
           100 * (month_close / lagInFrame(month_close) OVER (ORDER BY month_start) - 1) AS r
    FROM monthly
)
SELECT month,
       month_final_close,
       round(r, 2) AS simple_return_pct,
       round(100 * log(1 + r / 100), 2) AS log_return_pct
FROM rets
WHERE isFinite(r)
ORDER BY month_start

ข้อมูลรายเดือนสิบสองเดือน ตั้งแต่ 2.28% ใน 2025-07 ถึง -1.33% ใน 2026-06 โดยแถวสุดท้ายคือตัวเลข SPY ประจำเดือน มิถุนายน 2026 ชุดเดียวกับที่แผงแรกวัดค่าไว้ เมื่อคำนวณแบบทบต้นอย่างถูกต้องและเปรียบเทียบกับการใช้วิธีลัดด้วยการบวกเปอร์เซ็นต์เข้าด้วยกัน:

คำสั่งดึงข้อมูลSum เทียบกับ compound — การเชื่อมโยง 12 เดือนของ SPY monthly returns 3 รูปแบบ
SQL เบื้องหลังตัวเลขแต่ละตัว
WITH daily AS (
    SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS day,
           argMaxIf(toFloat64(close), window_start,
               toTimeZone(window_start, 'America/New_York') >= toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 09:30:00'), 'America/New_York')
               AND toTimeZone(window_start, 'America/New_York') < toDateTime(concat(toString(toDate(toTimeZone(window_start, 'America/New_York'))), ' 16:00:00'), 'America/New_York')) AS cl
    FROM global_markets.delayed_stocks_minute_aggs
    WHERE ticker = 'SPY'
      AND window_start >= '2025-06-24 04:00:00'
      AND window_start < '2026-07-01 08:00:00'
    GROUP BY day
),
monthly AS (
    SELECT toStartOfMonth(day) AS month_start,
           argMax(cl, day) AS month_close
    FROM daily
    GROUP BY month_start
),
rets AS (
    SELECT month_start,
           100 * (month_close / lagInFrame(month_close) OVER (ORDER BY month_start) - 1) AS r
    FROM monthly
),
ends AS (
    SELECT argMin(month_close, month_start) AS base_close,
           argMax(month_close, month_start) AS final_close
    FROM monthly
)
SELECT count() AS months_linked,
       round(sum(r), 2) AS simple_sum_pct,
       round(100 * (exp(sum(log(1 + r / 100))) - 1), 2) AS geometric_compound_pct,
       round(100 * (any(final_close) / any(base_close) - 1), 2) AS direct_twelve_month_pct,
       round(100 * (exp(sum(log(1 + r / 100))) - 1) - sum(r), 2) AS compounding_gap_points,
       round(sum(100 * log(1 + r / 100)), 2) AS sum_of_monthly_log_returns_pct,
       round(100 * log(any(final_close) / any(base_close)), 2) AS twelve_month_log_return_pct
FROM rets CROSS JOIN ends
WHERE isFinite(r)

ผลรวมสิบสองเดือนคือ 19.83% แต่เมื่อคิดแบบทบต้นจะได้ 20.79% และการคำนวณโดยตรงจากราคาปิดเดือน มิถุนายน 2025 ไปยังเดือน มิถุนายน 2026 จะได้ 20.79% ซึ่งตรงกับตัวเลขแบบทบต้นมากกว่าการใช้ผลรวม ส่วนต่างในที่นี้คือ 0.96 จุด ในปีที่มีความผันผวนต่ำ; ส่วนต่างนี้จะกว้างขึ้นตามความผันผวนและระยะเวลา การบวกเปอร์เซ็นต์รายเดือนเป็นนิสัยที่พบได้บ่อยในสเปรดชีต ซึ่งเป็นวิธีที่ผิด

สองคอลัมน์สุดท้ายแสดงวิธีการคำนวณที่เป็นมาตรฐานสำหรับการบวก นั่นคือ log return ซึ่งคือค่าลอการิทึมธรรมชาติของปัจจัยการเติบโต หรือ ln(1 + return) ผลรวมของ log return รายเดือนคือ 18.89% ซึ่งเท่ากับ log return สิบสองเดือนที่ 18.89% นี่คือเหตุผลที่นักวิเคราะห์และแบบจำลองความเสี่ยงนิยมใช้ค่านี้ สำหรับเดือนที่มีการเปลี่ยนแปลงน้อย วิธีการทั้งสองแทบไม่ต่างกัน (2025-11: 0.21% แบบธรรมดา, 0.21% แบบ log) แต่ยิ่งเดือนมีการเปลี่ยนแปลงมาก ส่วนต่างจะยิ่งกว้างขึ้น (2026-04: 10.49% แบบธรรมดา, 9.97% แบบ log) ทั้งนี้ ข้อมูลสรุปกองทุน (fund fact sheets) มักระบุผลตอบแทนแบบธรรมดา ส่วน log return มักใช้ในงานวิจัยและคณิตศาสตร์ด้านความผันผวน

รายการตรวจสอบเพื่อปรับข้อมูลจากสองแหล่งให้ตรงกัน

เมื่อตัวเลขผลตอบแทนรายเดือนจากสองแหล่งไม่ตรงกัน มักเกิดจากความแตกต่างในหนึ่งในสี่ปัจจัยหลัก ดังนี้:

  1. Endpoints — แบบ close-to-close (มาตรฐานทั่วไป) หรือแบบ open-to-close (การซื้อขายภายในเดือนนั้น) ข้อมูลจะต่างกันทันทีหากมีช่องว่างราคา (gap) ที่จุดเริ่มต้นหรือจุดสิ้นสุด
  2. Dividends — แบบ price return หรือแบบ total return ข้อมูลจะต่างกันในเดือนที่มีการขึ้นเครื่องหมาย ex-dividend
  3. Adjustment — แบบราคาดิบ (raw prints) หรือแบบราคาปรับปรุง (adjusted-close series) ข้อมูลจะต่างกันอย่างมากในเดือนที่มีการแตกหุ้น (split)
  4. The close itself — ราคาปิดจากการประมูลอย่างเป็นทางการ (มาตรฐาน) เทียบกับราคาจากการซื้อขายครั้งสุดท้ายซึ่งอาจรวมช่วงเวลาการซื้อขายนอกเวลาทำการ (extended hours)

หากใช้ปัจจัยเดียวกันกับข้อมูลทั้งสองแหล่ง ความคลาดเคลื่อนจะหมดไป การเปรียบเทียบระหว่างกองทุนกับดัชนีจะมีความสมบูรณ์ก็ต่อเมื่อตัวเลขทั้งสองใช้การตั้งค่าทั้งสี่แบบที่เหมือนกัน หากตั้งค่าไม่ตรงกันเพียงข้อเดียว การเปรียบเทียบนั้นจะกลายเป็นการวัดความแตกต่างของปัจจัยที่เลือกใช้แทนที่จะเป็นการวัดผลการดำเนินงาน สรุปผลเดือนมิถุนายน 2026 ของเราได้ระบุข้อกำหนดไว้ล่วงหน้าด้วยเหตุผลนี้ โดยตัวเลขรายเดือนทุกตัวในนั้นใช้แบบ close-to-close, ราคาปิดอย่างเป็นทางการ และแบบ price return

คำถามที่พบบ่อยเกี่ยวกับผลตอบแทนรายเดือน

Close-to-close return คืออะไร?

คือการเปลี่ยนแปลงเป็นเปอร์เซ็นต์จากราคาปิดในเซสชันปกติครั้งสุดท้ายของงวดก่อนหน้า มายังราคาปิดครั้งสุดท้ายของงวดปัจจุบัน นี่คือมาตรฐานสากลสำหรับการคำนวณผลตอบแทนหุ้นรายวัน รายเดือน และรายปี ในเอกสารข้อมูลสรุป (fact sheets) และรายงานดัชนี

ทำไมเว็บไซต์สองแห่งจึงแสดงผลตอบแทนของหุ้นและเดือนเดียวกันไม่เท่ากัน?

มักเกิดจากหนึ่งในสี่กรณีต่อไปนี้: การใช้จุดสิ้นสุดที่ต่างกัน (close-to-close เทียบกับ open-to-close), การนับรวมเงินปันผลหรือไม่นับ, การใช้ราคาดิบเทียบกับราคาที่ปรับปรุงตามการแตกหุ้น (split-adjusted), หรือการใช้แหล่งข้อมูลราคาปิดที่ต่างกัน ข้อมูลของ NVDA ในเดือนมิถุนายน 2026 มีค่าต่างกันระหว่าง -5.39% หรือ -7.4% จากการเปลี่ยนเกณฑ์เพียงอย่างเดียว

การแตกหุ้น (stock split) ทำให้การคำนวณผลตอบแทนรายเดือนเปลี่ยนไปหรือไม่?

ไม่ควรเปลี่ยน เนื่องจากการแตกหุ้นจะเปลี่ยนทั้งจำนวนหุ้นและราคาไปพร้อมกัน ทำให้มูลค่าของสถานะคงเดิม แต่การแตกหุ้นจะทำให้การคำนวณที่ใช้ราคาดิบผิดพลาด ข้อมูลของ NVDA ในเดือนมิถุนายน 2024 มีค่าเป็น -88.75% เมื่อใช้ราคาปิดดิบ และมีค่าเป็น 12.45% เมื่อปรับปรุงตามการแตกหุ้นในอัตรา 10-for-1 แล้ว

ผลตอบแทนหุ้นรายเดือนรวมเงินปันผลหรือไม่?

เฉพาะผลตอบแทนรวม (total returns) เท่านั้นที่รวม ส่วนผลตอบแทนด้านราคา (price returns) ซึ่งรวมถึงระดับดัชนี S&P 500 หลัก จะไม่รวมเงินปันผล ในเดือนมิถุนายน 2026 เงินปันผลได้เพิ่มค่า 0.25% ให้กับผลตอบแทนรายเดือนของ SPY ซึ่งเป็นส่วนต่างระหว่างราคาและผลตอบแทนรวม

ผลตอบแทนรายเดือนของพอร์ตโฟลิโอส่วนตัวฉันคำนวณด้วยวิธีเดียวกันหรือไม่?

ไม่ หากมีการเคลื่อนย้ายเงินสดเข้าหรือออกจากพอร์ต ผลตอบแทนของหลักทรัพย์เดี่ยวอย่างที่ปรากฏในหน้านี้ใช้การคำนวณแบบถ่วงน้ำหนักด้วยเวลา (time-weighted) ส่วนบัญชีที่มีการฝากและถอนเงินจำเป็นต้องใช้การคำนวณแบบถ่วงน้ำหนักด้วยเงิน (money-weighted หรือ internal-rate-of-return) มิฉะนั้นกระแสเงินสดจะทำให้ค่าผลตอบแทนคลาดเคลื่อน โบรกเกอร์ส่วนใหญ่จึงรายงานตัวเลขแบบถ่วงน้ำหนักด้วยเวลาเพื่อตัดรายการฝากเงินของคุณออกจากตัวเลขดังกล่าว


ตัวเลขทั้งหมดข้างต้นมาจากการดึงข้อมูล (query) ที่จัดเก็บและระบุเวอร์ชันจากข้อมูลตลาดจริง — คุณสามารถขยายคำสั่ง SQL ของแต่ละแผงข้อมูล หรือวัดผลตอบแทนรายเดือนของหุ้นใดก็ได้ภายใต้เกณฑ์ใดก็ได้บนเทอร์มินัล Strasmore

#returns#conventions#dividends#splits#education