PDA

View Full Version : java.lang.IllegalArgumentException



mohsen_dmz
سه شنبه 02 شهریور 1395, 17:18 عصر
]سلام و خشته نباشید. من کد زیر رو نوشتم و با این ارور روبرو شدم : java.lang.IllegalArgumentException.
من تازه کارم و چیزی از ارور ها نمیدونم ممنون میشم اگه کمک کنید.


private static InputStream URLInput;
private static URL address;
private static URLConnection myconnection;
private static InputStream URLinfo;
private static int c;

public static void main(String[] args) {
try{
address = new URL("http:\\www.google.com");
/*
System.out.println("basic information :");
System.out.println("protocol : " + address.getProtocol());
System.out.println("port : " + address.getPort());
System.out.println("host : " + address.getHost());
System.out.println("default port : " + address.getDefaultPort());
System.out.println("path : " + address.getPath());*/

try{
/* show web content*/
myconnection = address.openConnection();
//check to see if there is content
int contentlength = myconnection.getContentLength();
if (contentlength != 0){
System.out.print("content(s): \n\n");
URLinfo = myconnection.getInputStream();
while( (c = URLinfo.read() ) !=-1 ){
System.out.print((char) c);
}
URLInput.close();

}else{
System.out.println("sorry! there is no content");
}

}catch(Exception e){
System.out.println(e.toString());
}


}catch(Exception ex){
System.out.println(ex.toString());
}

vahid-p
چهارشنبه 03 شهریور 1395, 11:31 صبح
بهتره برای عیب یابی بهتر یک برنامه در catch ها، از printStackTrace() استفاده کنی (چیزی که IDE ها به صورت پیشفرض خودشون قرار میدن)
به هر حال خطایی که به شما میده:

java.lang.IllegalArgumentException: protocol = http host = null
که هاست رو نمیشناسه. و دلیلشم اینه شما آدرس رو اشتباه نوشتید.

http:\\www.google.com
غلطه و درستش

http://www.google.com
است. اگر اشتباه نکنم آدرس دهی فقط در سیستم عامل ویندوز از back slash (\) استفاده میشه و در سایر سیستم عامل ها از slash (/) برای آدرس دهی فایل ها استفاده میشه و URL هم از این قانون پیروی میکنه. همچنین از \ در رشته برای معرفی کاراکترهای خاصی استفاده میشه مثل n\ برای خط بعد و... (در خصوص رشته ها (http://www.tutorialspoint.com/java/java_strings.htm) بخونید)

این رو رعایت کنی، برنامت جواب میده اما چند تا نکته و مشکل داره کدت.
یکی از اشتباهات کد URLInput.close() در صورتی که هیچ جا چنین آبجکتی تعریف نشده. اگه برنامه به اونجا برسه NullPointerException میده
یکی از اشتباهات دیگه استفاده از getContentLength یا getContentLengthLong است. دلیلش اینه بسیاری از وبسایت ها همراه Response (پاسخ) طول بدنشون رو در content-length قرار نمیدن. در کد شما این مقدار برای -1 است اما چون شما نوشتید contentlength!=0 همیشه درسته هر چند منظورتون این نبوده! (مگر اینکه این هدر ست شده باشه و برابر 0 باشه چون اگر این هدر نباشه -1 خواهد بود). کلا در اکثر زبان ها مرسومه، هر چیزی که با خطا مواجه میشه یا به صورت اکسپشن اطلاع بدن (برای زبان هایی که اکسپشن رو پشتیبانی میکنن) یا -1 رو برگشت بدن (یا false و... بر حسب نوع متغیر).

حتما موقع استفاده کردن از یک متد، عملکردش رو بدونید. در جاواداک متد getContentLengthLong اومده:

Returns:

the content length of the resource that this connection's URL references, or -1 if the content length is not known

ضمنا بهتره به جای URLConnection از اونجایی که میدونی از HTTP استفاده میکنی، از HttpURLConnection استفاده کن. اونوقت متدی داری به اسم getResponseCode که اگر برای 200 بود یعنی بسته موفقیت آمیز بوده (و نیازی به دونستن content-length نیست)

بستن stream در finally هم که مفصل در اینترنت در موردش صحبت شده.

کد رو به این صورت تغییر میدم:


import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;


public class Main {


public static void main(String[] args) {
URL address = null;
HttpURLConnection myconnection = null;
InputStream uRLContent = null;
int c;


try {
address = new URL("http://www.google.com");
/*
System.out.println("basic information :");
System.out.println("protocol : " + address.getProtocol());
System.out.println("port : " + address.getPort());
System.out.println("host : " + address.getHost());
System.out.println("default port : " + address.getDefaultPort());
System.out.println("path : " + address.getPath());*/
/* show web content*/
myconnection = (HttpURLConnection) address.openConnection();
//check to see if there is content
int responseCode = myconnection.getResponseCode();
if (responseCode == HttpURLConnection.HTTP_OK) { // HttpURLConnection.HTTP_OK=200
System.out.print("content(s): \n\n");
uRLContent = myconnection.getInputStream();

while ((c = uRLContent.read()) != -1) {
System.out.print((char) c);
}
} else {
System.out.println("Sorry! There is a problem in connection");
}
} catch (MalformedURLException ex) {
ex.printStackTrace();
} catch (IOException ex) {
ex.printStackTrace();
} finally {
if(uRLContent!=null){
try {
uRLContent.close();
} catch (IOException ex) {
ex.printStackTrace();
}
}
}
}
}

اگر واقعا میخوای ببینی یک صفحه خالیه یا نه، علاوه بر اینکه باید بسته درست باشه (کد 200) میتونی در اون حلقه


while ((c = uRLContent.read()) != -1) {
System.out.print((char) c);
}
یک متغیر بذار و اگر وارد حلقه شد true کن یا نمیدونم مقدارش رو افزایش بده و بیرون حلقه میتونی بفهمی خالی بوده یا نه.
while ((c = uRLContent.read()) != -1) {
System.out.print((char) c);
}