← 返回博客列表 Optiver OA 真题解析:Trading Sequences + Order Book 模拟|一亩三分地高频面经
Optiver

Optiver OA 真题解析:Trading Sequences + Order Book 模拟|一亩三分地高频面经

2026-05-12

Optiver 是全球顶尖的做市商(Market Maker),其 OA 考察方向与传统科技公司有显著差异——除了标准的数据结构与算法,还会融入交易逻辑订单簿模拟概率推理等金融场景题。本文基于一亩三分地最新面经,系统拆解 Optiver OA 的核心题型与解题策略。

Optiver OA 概览

维度 详情
平台 HackerRank
时长 90 分钟
题量 2-3 道编程题
难度 Medium - Hard
考察重点 模拟、贪心、数学推理、低延迟思维

题型一:Trading Sequences(交易序列分析)

题目描述

给定一组交易价格序列 prices[] 和交易量 volumes[],需要找出满足特定条件的最优交易窗口。具体来说,你需要在序列中选择一个连续子区间 [l, r],使得该区间内的加权收益最大化。

解题思路

这道题本质上是加权最大子数组和的变体:

  1. 计算每个时间点的收益:profit[i] = (prices[i+1] - prices[i]) * volumes[i]
  2. 使用 Kadane's Algorithm 的变体求解最大连续子数组和
  3. 注意边界条件:交易窗口至少包含 2 个时间点

Python 解法

def max_trading_profit(prices, volumes):
    n = len(prices)
    if n < 2:
        return 0
    
    profits = [(prices[i+1] - prices[i]) * volumes[i] for i in range(n-1)]
    
    max_profit = float('-inf')
    current_sum = 0
    
    for p in profits:
        current_sum = max(p, current_sum + p)
        max_profit = max(max_profit, current_sum)
    
    return max(0, max_profit)

时间复杂度:O(n)
空间复杂度:O(n)

题型二:Order Book 模拟

题目描述

实现一个简化的订单簿系统,支持以下操作:

解题思路

这是一道设计 + 模拟题,核心数据结构选择:

Python 解法

import heapq
from collections import defaultdict

class OrderBook:
    def __init__(self):
        self.buy_orders = []   # max-heap (negate price)
        self.sell_orders = []  # min-heap
        self.cancelled = set()
        self.order_map = {}
        self.order_id = 0
    
    def add(self, side, price, quantity):
        self.order_id += 1
        order = (price, self.order_id, quantity)
        self.order_map[self.order_id] = order
        
        if side == 'BUY':
            heapq.heappush(self.buy_orders, (-price, self.order_id, quantity))
        else:
            heapq.heappush(self.sell_orders, (price, self.order_id, quantity))
        
        return self.order_id
    
    def cancel(self, order_id):
        if order_id in self.order_map:
            self.cancelled.add(order_id)
            return True
        return False
    
    def match(self):
        trades = []
        while self.buy_orders and self.sell_orders:
            # 清理已取消的订单
            while self.buy_orders and self.buy_orders[0][1] in self.cancelled:
                heapq.heappop(self.buy_orders)
            while self.sell_orders and self.sell_orders[0][1] in self.cancelled:
                heapq.heappop(self.sell_orders)
            
            if not self.buy_orders or not self.sell_orders:
                break
            
            best_buy = -self.buy_orders[0][0]
            best_sell = self.sell_orders[0][0]
            
            if best_buy >= best_sell:
                buy_order = heapq.heappop(self.buy_orders)
                sell_order = heapq.heappop(self.sell_orders)
                trade_qty = min(buy_order[2], sell_order[2])
                trade_price = best_sell
                trades.append((trade_price, trade_qty))
                
                # 部分成交处理
                if buy_order[2] > trade_qty:
                    heapq.heappush(self.buy_orders, 
                        (buy_order[0], buy_order[1], buy_order[2] - trade_qty))
                if sell_order[2] > trade_qty:
                    heapq.heappush(self.sell_orders, 
                        (sell_order[0], sell_order[1], sell_order[2] - trade_qty))
            else:
                break
        
        return trades

时间复杂度:ADD O(log n),CANCEL O(1),MATCH O(k log n)
空间复杂度:O(n)

题型三:Allocation(资源分配)

题目描述

给定 n 个交易员和 m 个交易机会,每个交易员有不同的资金上限和风险偏好。需要将交易机会分配给交易员,使得总收益最大化,同时满足每个交易员的约束条件。

解题思路

这是一个贪心 + 排序问题:

  1. 将交易机会按收益率降序排列
  2. 对每个交易机会,找到能承担该风险且资金充足的交易员
  3. 使用贪心策略分配
def allocate_trades(traders, opportunities):
    # traders: [(capital, risk_tolerance)]
    # opportunities: [(required_capital, risk_level, profit)]
    
    opportunities.sort(key=lambda x: -x[2])  # 按收益降序
    assigned = [False] * len(traders)
    total_profit = 0
    
    for cap_req, risk, profit in opportunities:
        best_trader = -1
        min_excess = float('inf')
        
        for i, (capital, tolerance) in enumerate(traders):
            if not assigned[i] and capital >= cap_req and tolerance >= risk:
                excess = capital - cap_req
                if excess < min_excess:
                    min_excess = excess
                    best_trader = i
        
        if best_trader != -1:
            assigned[best_trader] = True
            total_profit += profit
    
    return total_profit

Optiver OA 备考策略

核心能力要求

  1. 低延迟思维:Optiver 极度重视代码效率,O(n²) 在大数据量下不可接受
  2. 金融直觉:理解 bid/ask spread、order matching 等基本概念
  3. 边界处理:交易系统对精度和边界条件要求极高
  4. 并发意识:部分题目会考察对竞态条件的理解

推荐练习题

LeetCode 题号 题目 对应考点
53 Maximum Subarray Trading Sequences
1353 Maximum Number of Events Allocation
295 Find Median from Data Stream Order Book
480 Sliding Window Median 价格窗口分析

FAQ

Optiver OA 用什么平台?

Optiver 的 OA 通常在 HackerRank 上进行,时长约 90 分钟,包含 2-3 道编程题。部分岗位(如 Trader)还会有额外的数学和概率测试环节。

Optiver OA 难度如何?和 LeetCode 相比是什么水平?

Optiver OA 的编程题难度大约在 LeetCode Medium 到 Hard 之间,但题目风格偏向实际交易场景模拟,而非纯粹的算法竞赛题。需要候选人具备一定的金融市场基础知识。

Optiver SWE 和 Trader 的 OA 有什么区别?

SWE 岗位的 OA 侧重数据结构、算法和系统设计能力;Trader 岗位则更注重数学推理、概率计算和心算速度。两者都会涉及交易相关的场景题,但侧重点不同。

Optiver OA 之后的面试流程是什么?

通过 OA 后,通常会进入 HR 电话面试,然后是技术面试(1-2 轮),最后是 Superday(全天面试),包含系统设计、行为面试和团队匹配环节。

如何准备 Optiver 的交易模拟题?

建议先了解基本的做市商概念(bid-ask spread、order book、market making),然后练习堆、优先队列相关的 LeetCode 题目。同时可以参加 Optiver 的 Ready Trader Go 比赛来积累实战经验。


正在准备 Optiver OA?

oavoservice 提供专业的量化公司 OA/VO 辅助服务,覆盖 Optiver、Citadel、Jane Street 等顶级做市商。我们的团队成员来自各大量化机构,熟悉交易系统设计与算法面试。

👉 立即添加微信:Coding0201获取真题与辅助方案


联系方式

Email: [email protected]
Telegram: @OAVOProxy