Các lượt nộp
    Danh sách bài
    Trang chủ
    Báo lỗi

    solution

    Đề bài: [Trình biên dịch] Giảm cường độ toán tử bằng phép dịch bit

    Trong tối ưu hóa mã máy, phép nhân/chia cho lũy thừa của 2 có thể được thay bằng phép dịch bit (shift) vốn rẻ hơn nhiều so với phép nhân/chia thực sự, vì a×2k=a≪ka \times 2^k = a \ll ka×2k=a≪k, và với a≥0a \ge 0a≥0 thì ⌊a/2k⌋=a≫k\lfloor a / 2^k \rfloor = a \gg k⌊a/2k⌋=a≫k.

    Cho nnn lệnh mã ba địa chỉ dạng x = a op b với op∈{+,−,∗,/}op \in \{+,-,*,/\}op∈{+,−,∗,/}, trong đó a,ba,ba,b mỗi cái là một hằng số nguyên không âm hoặc tên biến. Với mỗi lệnh, hãy áp dụng đúng một quy tắc đầu tiên khớp trong danh sách theo thứ tự ưu tiên sau:

    1. Nếu opopop là * và đúng một trong hai toán hạng là hằng số bằng 2k2^k2k (k≥1k \ge 1k≥1) còn toán hạng kia là biến (không phải hằng số) → thay bằng x = <biến> << k.
    2. Nếu opopop là / và bbb là hằng số bằng 2k2^k2k (k≥1k \ge 1k≥1) còn aaa là biến (không phải hằng số) → thay bằng x = <biến> >> k (giả thiết biến đó luôn không âm lúc chạy).
    3. Nếu không quy tắc nào khớp, giữ nguyên lệnh gốc.

    Lưu ý quan trọng: 20=12^0 = 120=1 không được coi là lũy thừa của 2 hợp lệ cho quy tắc này (tức kkk phải ≥1\ge 1≥1); nếu cả hai toán hạng đều là hằng số, hoặc toán tử là +/-, lệnh luôn giữ nguyên.

    Ví dụ: x = 4 * y → x = y << 2 (vì 4=224=2^24=22); x = y / 4 → x = y >> 2; x = 3 * y giữ nguyên (3 không phải lũy thừa của 2); x = y * 1 giữ nguyên (20=12^0=120=1 không hợp lệ).

    • Định dạng đầu vào:
      • Dòng đầu: số nguyên nnn (0≤n≤10000 \le n \le 10000≤n≤1000).
      • nnn dòng tiếp theo, mỗi dòng đúng định dạng x = a op b (các token cách nhau đúng một khoảng trắng), op∈{+,−,∗,/}op \in \{+,-,*,/\}op∈{+,−,∗,/}; a,ba,ba,b là số nguyên không âm (0≤⋅≤2300 \le \cdot \le 2^{30}0≤⋅≤230) hoặc tên biến (chuỗi chữ cái/số, ký tự đầu là chữ cái).
    • Định dạng đầu ra:

      In ra nnn dòng, mỗi dòng là lệnh sau khi áp dụng quy tắc (giữ đúng định dạng x = ..., dùng << hoặc >> khi có thay đổi). Nếu n=0n=0n=0 thì không in gì.

    Ví dụ:

    Đầu vào:

    0
    

    Đầu ra:

    Đầu vào:

    6
    x = 4 * y
    x = y * 8
    x = y / 4
    x = 3 * y
    x = 2 * 3
    x = y + z
    

    Đầu ra:

    x = y << 2
    x = y << 3
    x = y >> 2
    x = 3 * y
    x = 2 * 3
    x = y + z
    

    Đang tải editor...