編輯 | 言征
出品 | 51CTO技術(shù)棧(微信號(hào):blog51cto)
近日,OpenAI一記重拳,推出了GPT-4o(“o”表示“omni”),將語(yǔ)音識(shí)別和對(duì)話方面的優(yōu)勢(shì)展示的淋漓盡致。幾乎可以肯定,它也是一個(gè)更強(qiáng)的LLM。但它能進(jìn)行代碼審查嗎?本文通過(guò)一些測(cè)試來(lái)尋找答案。
1.長(zhǎng)乘法:交給計(jì)算機(jī)就可以
首先,我檢查了它是否可以進(jìn)行l(wèi)ong乘法運(yùn)算:
圖片
答案是正確的,通過(guò)在線計(jì)算器上可以確認(rèn)。但請(qǐng)注意,它并沒(méi)有試圖“計(jì)算出”結(jié)果——它只是將問(wèn)題甩給了計(jì)算器。末尾的“查看分析”的藍(lán)色圖標(biāo)基本上說(shuō)明了這一點(diǎn)。這在之前的模型上都沒(méi)有做到。
2.代碼審查
我個(gè)人對(duì)正式嚴(yán)謹(jǐn)?shù)拇a審查沒(méi)有興趣。是的,有時(shí)初級(jí)開(kāi)發(fā)人員可能確實(shí)需要這樣的審查,但單元測(cè)試和配對(duì)編程通常足以消除不良的編程習(xí)慣。但是,幾句含糊的評(píng)論可以幫助指出代碼中的潛在小問(wèn)題,而不會(huì)顯得對(duì)容易重寫的代碼片段強(qiáng)加某種權(quán)威性的命令。
簡(jiǎn)而言之,代碼審查更多的是一種social互動(dòng),而不是其他任何東西。請(qǐng)專注于工程問(wèn)題,而不是代碼的語(yǔ)義細(xì)節(jié)。
然而,代碼審查是開(kāi)發(fā)人員使用大型語(yǔ)言模型(LLM)的一個(gè)好案例。在這里,我將查看三段不同的代碼,每段代碼都只是繪制一個(gè)帶有對(duì)角線的矩形框。我將添加問(wèn)題,并查看GPT-4o(通過(guò)ChatGPT)如何對(duì)它們進(jìn)行審查。
接下來(lái),我們從簡(jiǎn)單的C#對(duì)角線繪制程序開(kāi)始:
using System;
public class Program
{
public static void Main()
{
BoxWithDiagonalLine(5);
BoxWithDiagonalLine(6,1);
BoxWithDiagonalLine(6,-1);
BoxWithDiagonalLine(2);
BoxWithDiagonalLine(-1);
}
// Example 1
public static void BoxWithDiagonalLine(int boxsize, int linepos = 0)
{
for(int i=0; i < boxsize; i++)
{
for (int j = 0; j < boxsize; j++)
{
if (j == linepos) Console.Write("x ");
else Console.Write("o ");
}
linepos++;
Console.Write("n");
}
Console.Write("n");
}
}
將這個(gè)代碼丟進(jìn)https://dotnetfiddle.net/(不過(guò)請(qǐng)將編譯器設(shè)置為至少.NET 6)并查看響應(yīng):
圖片
這段代碼相當(dāng)簡(jiǎn)單,也相對(duì)容易理解。外部循環(huán)控制行,內(nèi)部循環(huán)在正確的位置放置“x”。變量命名很簡(jiǎn)潔,代碼很短。該方法有一個(gè)默認(rèn)值,用于生成從左上角到右下角的完整對(duì)角線。雖然我們可以將起始線位置向左或向右移動(dòng),但擁有負(fù)的盒子大小(boxsize)并沒(méi)有多大意義。因此,我們可以通過(guò)將方法參數(shù)更改為無(wú)符號(hào)整數(shù)(unsigned int)來(lái)改進(jìn)它。這將立即阻止上一個(gè)示例甚至無(wú)法編譯。一個(gè)非常大的linepos(起始線位置)將不可見(jiàn),但它并不危險(xiǎn)。
到目前為止,沒(méi)有什么可評(píng)論的。
接下來(lái),將for循環(huán)替換成while循環(huán):
// Example 2
public static void BoxWithDiagonalLine(int boxsize, int linepos = 0)
{
int i = 0;
while(i++ < boxsize)
{
int j = 0;
while (j++ < boxsize)
{
if (j == linepos + 1) Console.Write("x ");
else Console.Write("o ");
} linepos++;
Console.Write("n");
}
Console.Write("n");
}
現(xiàn)在這段代碼可以運(yùn)行,但值得稍微皺一下眉頭。通過(guò)在后置遞增循環(huán)變量(在i和j后面的++意味著值首先被讀取,然后再增加1)我們節(jié)省了一些空間,但我們需要那個(gè)笨拙的linepos + 1表達(dá)式。
while循環(huán)不如for循環(huán)那樣明確地表達(dá)開(kāi)始和結(jié)束狀態(tài)——但我們并沒(méi)有陷入任何瘋狂的狀態(tài)。
我們進(jìn)行最后一次更改。這次代碼中有一個(gè)變量來(lái)“搗亂”,它試圖使用linepos來(lái)控制外部循環(huán):
//Example 3
public static void BoxWithDiagonalLine(int boxsize, int linepos = 0)
{
while(linepos < boxsize)
{
int j = 0;
while (j++ < boxsize)
{
if (j == linepos + 1) Console.Write("x ");
else Console.Write("o ");
}
linepos++;
Console.Write("n");
}
Console.Write("n");
}
在試圖不必要地移除一個(gè)循環(huán)變量的過(guò)程中,矩形框本身將不再完整——盡管使用默認(rèn)值時(shí)可以工作。事實(shí)上,這解決了另一個(gè)問(wèn)題,即總是在底部角落可靠地以一個(gè)“×”結(jié)束。
圖片
這段糟糕的代碼可能是因?yàn)殚_(kāi)發(fā)者不當(dāng)?shù)乩^續(xù)使用了while循環(huán)。
現(xiàn)在讓我們總結(jié)一下我們?nèi)绾慰创@些不同版本:
第一個(gè)例子是可行的,但我們可以強(qiáng)制參數(shù)為正數(shù)。然而,沒(méi)有注釋的話,這段代碼的功能并不十分清晰。
第二個(gè)例子使用了while循環(huán),它不像for循環(huán)那樣具有確定性。同時(shí),由于后置遞增,還需要考慮一個(gè)丑陋的表達(dá)式。
第三個(gè)例子完全是錯(cuò)誤的,盡管在默認(rèn)情況下它得到了正確的結(jié)果。
我們對(duì)AI代碼審查有什么期望?首先,我沒(méi)有給出任何注釋,那么它能否弄清楚這段代碼的作用?只有方法的名稱揭示了這一點(diǎn)。
這是GPT-4o的回應(yīng):
“Your code is functional and effectively generates a box with diagonal lines based on the provided parameters. However, there are a few improvements and edge cases to consider:
1.Input Validation: Ensure that the box size is positive and greater than 1, since a box with a size less than 2 doesn’t make much sense.
2.Handling linepos: Improve handling of diagonal positions to ensure the diagonals are correctly drawn when linepos is negative or greater than the box size.
3.Code Readability: Add comments and improve variable naming for better readability and maintenance.”
【譯】“您的代碼是功能性的,并且能夠有效地根據(jù)提供的參數(shù)生成帶有對(duì)角線的矩形框。但是,有幾個(gè)改進(jìn)點(diǎn)和邊緣情況需要考慮:
1.輸入驗(yàn)證:確保矩形框的大小是正數(shù)且大于1,因?yàn)榇笮⌒∮?的矩形框并沒(méi)有太大意義。
2.處理linepos:改進(jìn)對(duì)角線位置的處理,以確保當(dāng)linepos為負(fù)數(shù)或大于矩形框大小時(shí),對(duì)角線能夠正確繪制。
3.代碼可讀性:添加注釋并改進(jìn)變量命名以提高代碼的可讀性和可維護(hù)性?!?/p>
所以它確實(shí)理解了代碼的作用——即使它認(rèn)為程序畫的是“l(fā)ines”而不是“l(fā)ine”。這仍然很好。
它建議的代碼如下:
// ChatGPT4o suggested code
public static void BoxWithDiagonalLine(int boxSize, int linePos = 0)
{
if (boxSize < 2)
{
Console.WriteLine("Box size must be greater than 1.");
return;
}
// Adjust linePos if it's out of the box boundaries
if (linePos < 0) linePos = 0;
if (linePos >= boxSize) linePos = boxSize - 1;
for (int i = 0; i < boxSize; i++)
{
for (int j = 0; j < boxSize; j++)
{
if (j == linePos) Console.Write("x ");
else Console.Write("o ");
}
linePos++;
// Reset linePos if it goes out of the box boundaries
if (linePos >= boxSize) linePos = 0;
Console.Write("n");
}
Console.Write("n");
以下是將其放入dotnetfiddle.net的結(jié)果:
圖片
我認(rèn)為大多數(shù)人都會(huì)對(duì)小于2的boxSize感到滿意。同時(shí),它也很好地使用了駝峰命名法來(lái)命名參數(shù),這在C#中是正確的。但遺憾的是,它忽略了改變位置以使線條從更低處開(kāi)始的想法。而由于重置了linepos,我們?cè)诘诙€(gè)例子的底部得到了那個(gè)糟糕的錯(cuò)誤。
不過(guò),從代碼審查的角度來(lái)看,它確實(shí)抓住了要點(diǎn)。
3.第二個(gè)例子結(jié)果
讓我們給它輸入第二個(gè)例子,看看它的表現(xiàn)如何。下面是一些有趣的評(píng)論:
“The use of while loops is functional but could be less intuitive compared to for loops for such iterations.”
Excellent. This is exactly the right note.
“The condition j == linepos + 1 is used to determine where to place “x”. This works but can be made more intuitive by aligning with the index i.”
再次強(qiáng)調(diào),這是很好的。它理解了功能性和可讀性之間的區(qū)別。
生成的代碼限制了linepos的值,并且相當(dāng)奇怪地使用了取模函數(shù)來(lái)改變這個(gè)值。但最終得到了相同的結(jié)果。它回歸到了for循環(huán),這是很棒的。
4.第三個(gè)例子結(jié)果
最后,讓我們給出糟糕的例子3,看看它的表現(xiàn)如何。奇怪的是,它沒(méi)有發(fā)現(xiàn)這個(gè)錯(cuò)誤,但提出了以下建議:
“Edge Cases:
– When linepos is negative, it works but may not be intended.”
這表明它完全沒(méi)有理解代碼——當(dāng)然,我也沒(méi)有明確說(shuō)明我在做什么。所以,也許“wrapping line ”可能是一個(gè)合理的猜測(cè)?
5.結(jié)論
總的來(lái)說(shuō),審查的性質(zhì)和結(jié)果給我留下了深刻的印象。GPT-4o生成的代碼雖然不太理想,但也還可以。在對(duì)代碼的批評(píng)中,沒(méi)有“書呆子的笨拙腳步”;相反,它輕輕地引導(dǎo)讀者走向更好的方向。
結(jié)果可能沒(méi)有達(dá)到預(yù)期——態(tài)度很好但代碼略有不準(zhǔn)確。然而,新手應(yīng)該會(huì)很喜歡;在這方面,它至少比部分人做得更好。
參考鏈接:https://thenewstack.io/reviewing-code-with-gpt-4o-openais-new-omni-llm/