【筆試在線編程踩的坑】--- OJ常見問題

引言

最近參加了幾場筆試,可能是備戰不足吧,被一些題目的輸入輸出給絆倒了,浪費了很多時間,甚至有些題直接通過0測試用例,但是自己的算法和代碼完全沒毛病,下來查閱資料,仔細梳理了一些關於輸入輸出的常見問題分享給大家。

關於牛客網

牛客網相信各位小夥伴都很熟悉吧,“要入職,先上牛客網”,上邊有一期關於輸入輸出的競賽,我覺得很不錯,尤其是對於像我這種編程“小白”來說很有用,練習常見的輸入輸出問題!!!
牛客網輸入輸出練習(點擊進入:https://ac.nowcoder.com/acm/contest/320)
在這裏插入圖片描述

OJ概念

online judge,簡稱OJ,是一個在線的判題系統。用戶可以在線提交多種程序代碼(比如:C、C++、Java、Python等),系統對源代碼進行編譯和執行,並通過預先設計的測試用例來檢驗程序源代碼的正確性。現廣泛應用於世界各地高校學生程序設計的訓練、作業的自動提交判斷,以及各種競賽(比如ACM)等。

OJ原理

用戶提交的程序在OJ系統下執行時將受到比較嚴格的限制,包括運行時間限制,內存使用限制和安全限制等。用戶程序執行的結果將被OJ系統捕捉並保存,然後再轉交給一個裁判程序。該裁判程序或者比較用戶程序的輸出數據和標準輸出樣例的差別,或者檢驗用戶程序的輸出數據是否滿足一定的邏輯條件。最後系統返回給用戶一個狀態:通過、答案錯誤、超時、超過輸出限制、超內存、運行時錯誤、格式錯誤、或是無法編譯,並返回程序使用的內存、運行時間等信息。

循環輸入輸出處理常見問題

1、爲什麼需要循環輸入輸出:通常來說OJ對於每道題裏面有.in和.out文件,分別表示測試數據的輸入和輸出。如果某些編程題的所有數據都只做在一個.in和一個.out中,這樣就會變成多組測試了,所以需要提交的代碼中循環處理。

2、處理方法:其實這個問題可以避免,就是編程題後臺每個樣例做一組對應的.in和.out文件,這樣就變成單組測試,代碼就不需要循環處理,但是平時練習的題目質量不一,這個問題都會出現。代碼裏面循環處理了即使是單組測試也會完全沒問題,所以爲了偷懶,可以全寫成循環處理。

3、大坑:如果測試數據是多組的,但是恰巧你代碼裏面需要些標記數組,map,set等,在循環內一定記得清空,不然可能會產生前面的測試樣例影響了後續數據的答案。

對於各種語言的一些基本知識

1、出題人通常會使用C/C++編寫標程,數據也是由標程製造的,所以使用跟出題人一樣的語言會比較穩妥

2、C/C++效率比較高,通常來說一般OJ對於一道題目的時限限制會區分C/C++和其他語言,通常處理方式是假設C/C++時限是1s,其他語言就會給2倍時限,甚至更多。

3、關於cin cout和scanf printf。做題的時候儘量使用scanf printf。下面告訴一個小常識,不要驚訝:在數據量比較大的情況下cin cout比scanf printf慢挺多。一旦遇到大數據量,光是讀入就有可能跪掉。你或許可以使用std::ios::sync_with_stdio(false); 這條語句關掉scanf和cin的同步,加快效率。但是即使這樣cin還要慢,而且一旦使用了這條語句,scanf和cin混用可能就會造成一些奇怪的錯誤

4、Java相關:Java整體效率大概比C/C++慢2倍以上,但是Java寫編程題也沒什麼問題,主要就是處理好各種輸入輸出的情況。

5、python等等其他語言,做編程題首先要自己在平臺上多練習不同的數據格式的讀取方法,還有就是效率可能偏低,另外有些語言封裝的功能太豐富了,以至於代碼裏各種函數完成的最終代碼,筆試官或者面試官對於算法的考察並不想看到這樣的code。

6、開闢數組空間最好根據題目的數據範圍要求來,這裏可能會造成runtime error,如果代碼中遞歸的深度太深也可能爆棧空間導致runtime error。

關於輸出格式

1、行末空格:比如我輸出需要打印多個數需要使用空格分隔的時候,我們循環使用printf("%d ",x);這種會很方便,但是這樣會導致行末多一個空格,後臺系統會嚴格比對你的輸出和.out文件,這樣也會被判錯誤
2、換行問題,對於每個樣例,建議輸出完全之後都換行一下。對於一些題目,可能就是不換行就導致了後面輸入數據錯位,那就肯定不可能過了。

關於時間複雜度分析

通常來說一般的系統1s能跑的算法量級是不足1e8的,所以做題的時候評估算法效率很重要,直接判斷你的做法能否通過,當然這是以C/C++爲標準的,其他語言自己乘個時間倍數。。

舉個例子,比如題目n = 1e5,那麼我就可以很敏感的知道我的算法需要一個 O(n) 或者 O(nlogn)。平方複雜度直接超時!

關於 “我本地能通過,交上去就是不對”

提交不成功,一般就兩種情況

  1. 代碼語法問題,導致編譯不同過
    a.多去刷題,將常犯的錯誤積累下來
    b.避免使用一些奇怪的函數,或者與平臺相關的函數
    c.最好不要使用vs來寫算法,vs默認是Windows下的方式,一般OJ編譯器可能無法識別
  2. 代碼編譯成功,提交不成功
    a.查看輸出不成功的信息,輸出格式不對還是無法通過某個測試用例
    b.對於無法通過的測試用例,一般都會將無法通過的用例顯示出來,然後提供一個本該輸出與程序輸出,通過輸出結果以及測試用例,檢查代碼那塊有誤。
    c.實在檢查不出來,逐個測試用例處理
  3. 自己編譯器可以執行,但是OJ不可以通過
    如有部分同學會說,在自己的編譯器上可以跑通代碼,但是在OJ上面不可以提交原因是什麼?這種問題有很
    多種,比如傳入的參數沒有進行合法檢查,例如:指針沒有判空等等。這種問題大多是這些邊界的問題

本文參自(https://www.nowcoder.com/discuss/8632)

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章