剛學(xué)Java不久,這里記錄日常工作和學(xué)習(xí)中遇見的問題国拇,都是入門級知識點庆锦。
1. Uninstall intellij
由于本地的Jetty一直跑不起來,已經(jīng)影響到日常的開發(fā)工作怒见,在報錯實在沒有辦法解決的情況下,只能選擇格式化重來姑宽,在此我表示很傷心速种。好吧,那就傷心地記錄下intellij idea卸載的過程
macos上選擇應(yīng)用程序intellij低千,將其移動到廢紙簍里面配阵,這樣其實不能干凈卸載intellij,按照下面步驟可以清理干凈:
rm -rf /Library//Preferences/IdeaIC13
rm -rf /Library//Caches/IdeaIC13
rm -rf /Library//Application Support/IdeaIC13
rm -rf /Library/Logs/IdeaIC13
清理掉Config, System, Plugins, Logs 應(yīng)該就干凈了示血。
2. Maven Jetty啟動報錯:PermGen space
報錯內(nèi)容如下:
[INFO] Started Jetty Server
[INFO] Starting scanner at interval of 20 seconds.
But at the first scan i get the following error:
ERROR ContextLoader - Context initialization failed
java.lang.OutOfMemoryError: PermGen space
解決方法棋傍,加上:-Xmx1024m -Xms1024m -XX:PermSize=512m
有時候我們需要遠程調(diào)試,IDea支持遠程調(diào)試功能:
將Host和Port改成遠程機器的IP和端口难审,那么遠程JVM啟動的時候加上參數(shù):
JVM_ARGS ="****(其他參數(shù)) -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8417"
3. Java 主線程和子線程的關(guān)系
Java認為:并不存在java的主線程和子線程之分瘫拣,都只是個普通的線程。進程的資源是線程共享的告喊,只要進程還在麸拄,線程就可以正常執(zhí)行派昧,換句話說線程是強依賴于進程的。也就是說拢切,線程其實并不存在互相依賴的關(guān)系蒂萎,一個線程的死亡從理論上來說,不會對其他線程有什么影響淮椰。JVM可以理解為進程五慈,只要JVM還在線程就有執(zhí)行的機會。
這點跟Golang不同主穗,Golang里面主協(xié)程一旦退出泻拦,子協(xié)程就沒有執(zhí)行的機會了,Golang是通過Channel完成多協(xié)程之間的通信忽媒。
4. Java 多線程的創(chuàng)建
(1) 繼承Thread
class CustomThread extends Thread {
@Override
public void run() {
System.out.println("子線程ID:"+Thread.currentThread().getId());
System.out.println("我繼承Thread類争拐,處理任務(wù)的邏輯");
}
}
public class MoreThread {
public static void main(String[] args) {
System.out.println("主線程ID:"+Thread.currentThread().getId());
new CustomThread().start();
}
}
(2) 實現(xiàn)Runnable
class MyThread implements Runnable {
@Override
public void run() {
System.out.println("子線程ID:"+Thread.currentThread().getId());
System.out.println("我實現(xiàn)Runnable接口, 處理任務(wù)的邏輯");
}
}
public class MoreThread {
public static void main(String[] args) {
System.out.println("主線程ID:"+Thread.currentThread().getId());
new Thread(new MyThread()).start();
}
}
(3) ExecutorService、Callable晦雨、Future有返回結(jié)果的多線程
class CallableImpl implements Callable<Integer> {
public Integer call() throws Exception {
Integer sum = 0;
System.out.println("Callable子線程開始計算啦架曹!");
for (int i=0; i<50; i++){
sum = sum + I;
}
System.out.println("Callable子線程計算結(jié)束!");
return sum;
}
}
public class MoreThread {
public static void main(String[] args) {
ExecutorService executorService = Executors.newSingleThreadExecutor();
CallableImpl callable = new CallableImpl();
Future<Integer> future = executorService.submit(callable);
executorService.shutdown();
try{
Thread.sleep(2000);
System.out.println("主線程有其他任務(wù)在執(zhí)行");
if (future != null && future.get() != null) {
System.out.println("future.get()-->"+future.get());
} else {
System.out.println("future.get()未獲取到結(jié)果");
}
}catch (Exception e) {
e.printStackTrace();
}
System.out.println("主線程在執(zhí)行完成");
}
}
5. Java 泛型
Java泛型出來之前金赦,java是如何做泛型的呢?
private static void print(Object object) {
System.out.println(object.getClass().getName().toString());
if (object instanceof Integer) {
System.out.println(1);
} else if (object instanceof String) {
System.out.println("cd1");
}
}
是的对嚼,通過反射或者強制類型轉(zhuǎn)化來達到類型匹配的目的夹抗。Java中的Object
就相當(dāng)于Golang中的interface
,容納一切類型纵竖。
Java的泛型非常強大漠烧,強大到無處不在。同時Java的泛型只在編譯階段有效靡砌,在編譯之后程序會采取去泛型化的措施已脓。也就是說Java中的泛型,只在編譯階段有效通殃。在編譯過程中度液,正確檢驗泛型結(jié)果后,會將泛型的相關(guān)信息擦出画舌,并且在對象進入和離開方法的邊界處添加類型檢查和類型轉(zhuǎn)換的方法堕担。也就是說,泛型信息不會進入到運行時階段曲聂。http://www.reibang.com/p/95f349258afb 和http://blog.csdn.net/s10461/article/details/53941091文章寫得不錯霹购。
Java中泛型分為:泛型類,泛型方法朋腋,泛型接口三大類齐疙。Java的泛型通配符?, T, K,V,E的含義:
膜楷? 表示不確定的java類型
** T (type)** 表示具體的一個java類型
K V (key value) 分別代表java鍵值中的Key Value
E (element) 代表Element
6. Maven
maven是java中非常棒的包管理工具,如果你想發(fā)布一個jar包到平臺上去贞奋,只需要執(zhí)行:mvn deploy
赌厅。但經(jīng)常會出現(xiàn):
Error occurred during initialization of VM
Too small initial heap
解決方法:
export MAVEN_OPTS=-Xmx1024m
加到環(huán)境變量里面,然后 source /etc/profile
即可忆矛。
7. ThreadLocal
先給出它的用途察蹲,ThreadLocal和Synchonized都用于解決多線程并發(fā)訪問。但它們有本質(zhì)的不同催训,Synchronized用于線程間的數(shù)據(jù)共享洽议,而ThreadLocal則用于線程間的數(shù)據(jù)隔離。
這里想問一個問題漫拭,Golang為什么不搞一個thread local storage呢亚兄?Rob Pike先生是如何看待threadLocal這個東西的呢?
8. DispatcherServlet
Spring是通過DispatcherServlet ->FrameworkServlet->HttpServletBean->HttpServlet->GenericServlet->Servlet,最終實現(xiàn)了Servlet接口采驻,DispatcherServlet又叫前置控制器审胚。DispatcherServlet的主要工作流程如下:
- 前端請求到達DispatcherServlet。
- 前端控制器請求HandlerMappering 查找Handler礼旅。
- 如果查找到存在的處理器膳叨,進一步去調(diào)用service和dao層
- 返回結(jié)果再到controller層,渲染具體的視圖痘系,返回結(jié)果給頁面菲嘴。
9. Synchronized
類方法中synchronized鎖住的是對象this,只有調(diào)用同一個對象的方法才需要獲取鎖汰翠。
靜態(tài)方法中synchronized鎖住的是類龄坪,該類中所有加了synchronized的靜態(tài)方法,一次只能調(diào)用一個复唤。
這里必須強調(diào)的是:當(dāng)一個對象被創(chuàng)建時候健田,JVM會為這個對象創(chuàng)建一個自引用的指針this,所以this只能在類的非靜態(tài)方法中使用佛纫,this和對象之間是一一對應(yīng)關(guān)系妓局,不是和類一一對應(yīng),這個需要特別注意的點呈宇。同一個類的不同實例(對象)this不是一個東西跟磨。
10. JVM鎖優(yōu)化
對象鎖的狀態(tài)分為四種: 無鎖,輕量級鎖攒盈,重量級鎖和偏向鎖抵拘。偏向鎖是JDK1.6提出來的一種鎖優(yōu)化的機制,默認是開啟的型豁。這么多鎖的目的是為了盡可能提高鎖的性能僵蛛,降低鎖帶來的系統(tǒng)性能損耗尚蝌。http://blog.csdn.net/zhxdick/article/details/61916359
11. Java Reference
Java的引用分四個級別:強,軟(SoftReference)充尉,弱(WeakReference)飘言,虛(PhantomReference);
強引用就是普通引用驼侠,A a1=new A(); A a2 = a1; 當(dāng)所有A的引用a1, a2都失效之后姿鸿,new出來的A()對象才能被回收。如果對象的內(nèi)存大小超出之后倒源,直接報“java.lang.OutOfMemoryError”苛预。
軟引用用來描述還有用并非必要的對象,在系統(tǒng)將要發(fā)生內(nèi)存溢出異常之前笋熬,將會把這些對象列入回收范圍進行第二次回收热某。如果這次回收還沒有足夠的內(nèi)存,才會拋出內(nèi)存溢出異常胳螟。
弱引用也是用來描述非必要對象的昔馋,但是他的強度比軟引用更弱一些,被軟引用關(guān)聯(lián)的對象只能生存到下一次垃圾收集發(fā)生之前糖耸。當(dāng)垃圾收集器工作時秘遏,無論當(dāng)前內(nèi)存是否足夠,都會回收掉只被弱引用關(guān)聯(lián)的對象嘉竟。
一個對象是否有虛引用的存在邦危,完全不會對其生存時間構(gòu)成影響,也無法通過虛引用來獲取一個對象的實例周拐。為一個對象設(shè)置虛引用關(guān)聯(lián)的唯一目的就是能在這個對象被收集器回收時收到一個系統(tǒng)通知铡俐。