- 我會利用 Lindy Effect 來挑選要閱讀的書籍:當一本書已經存活超過十年,其一定會再存在十年,當一本書已存在兩千年,其想必會存在很長的時間。每天說看到成千上百的新聞或報章雜誌,都只是雜訊而已,儘管在發表的時候非常轟動,但僅能存活非常短的時間。
- 最好的方法是時間,時間是揭穿脆弱性、強固與反脆弱性的絕佳過濾器。時間是雜訊的清潔工(多如牛毛的學術論文、垃圾雜誌、偽科學、偽君子、金融騙子...),隨著時間推移,脆弱會降低,留下強固的事物,以及歷久彌堅的反脆弱事物。「對於反脆弱的事物來說,已經存在五百年的東西,會再存在五百年,而且比預言它會滅亡的人活得更久。」
- 我們周遭有哪些是脆弱的呢?大型的、經最佳化的、過度仰賴科技的、過度仰賴所謂的科學方法而非經過時間驗證的,都是脆弱的事物。當今的大公司,未來將會修施,它們會因為他們自認為的優勢 (也就是 size) 而變脆弱,size 是企業的敵人,在 Black Swans 前更顯脆弱
- 曾有人問愛因斯坦,是否會隨時記下自己的想法,愛因斯坦的回答是:我從來沒有想法,但其實他只是沒有無足輕重的想法而已。作者告訴我們:人的腦袋不能裝太多複雜的技巧和方法,這樣往往會讓人忽略最基本的東西。
- 政府與醫療都是在極端狀態下才應該介入與干預。干預的決策不應根據知識,而是根據代價 (payoff)
- 短時間內沒有證據證明有害不等於無害,在深奧系統運作當中,只有時間-一段很長的時間之後,才會給我們證據
- 反脆弱藉着凸性得益,可靠試誤法和試探啟發法(heuristic) 在隨機中進步。試誤法的要點之一是,每次都是小的錯誤,所失有限,卻所得可貴,能改進以後的選擇。可是我們的世界,有很多連結極深的事物,是不容小錯的,我們為了效率優化,將架構變得有上而下、中心化,但就變得脆弱了。例如,航空業能在每次飛機失事中學得教訓,使之後的航程更安全,因為一架飛機出事,不會令其他飛機都出事,錯誤不會發展開來。可是銀行業的盤根錯節關係,卻會因為一間銀行倒閉,而帶來連鎖效應,於是產生了「大到不能倒」的冤大頭。去中心化,由下而上是反脆弱之道。另一策略是備餘,或許可看成是過度補償的結果。我們的身體就有很多備餘:兩隻手、兩對眼、兩個肺、兩個腎等等,使我們在意外後仍有較大可能生存,對抗錯誤。
- 這種“你有證據嗎”的謬論是將『證明無害的證據』與『缺乏證據證明有害』混為一談,與我們將 NED (No Evidence of Disease,缺乏證據證明某種疾病) 曲解為『有證據證明無某種疾病』的情況相類似,與將缺乏證明某事存在的證據視為證明某事不存在的證據相類似。這種錯誤往往會影響到受過教育的聰明人,就好像教育使人們更傾向于以證實思維做出反應,更容易陷入簡單的邏輯誤區。我們不應該讓健康的人去冒險;但是,對於那些被認為處於危險之中的人,則應該冒更多的風險。這裡的陳述都是以風險管理為基礎的:如果一個人的病情十分嚴重,就無須擔心醫源性損傷了。
- 塔雷伯介紹醫療傷害(Iatrogenics),由治療而受到傷害(通常是隱形或延後出現)的傷害超過利益,書中不只狹義針對醫療行為中的傷害,而是廣泛存在於社會環境中,利益小且可見,成本卻很大、延後和隱形的危險情況。換言之,書中反而建議應盡可能減少不必要的干預,還諸自然的反脆弱性。塔雷伯相信人類本身具有反脆弱性,主張否定法,但他並非反對干預,而是反對天真干預和不夠多的干預 (在真正需要的時候)。
- 醫療傷害 (iatrogenics) 是針對病患 (patient) 而非療法 (treatment)。若病患已病入膏肓,任何有可能的療法都應去嘗試。相反的,若病患近乎健康,則應師法大自然,讓其順其自然,不需過度治療
- 百憂解是一類名為選擇性血清素再攝取抑制劑 (SSRI) 的新型藥物中的明星產品。其作用基於的觀念為,抑鬱症是由一種名叫血清素的神經遞質不足引起的。只要能提高這種腦化學物質的濃度,精神一下子就振奮起來了。事實上,已經有成百上千萬人接受了百憂解,並對它的作用深信不疑。但凡事都是十年河東十年河西,百憂解也不例外。起初它被尊為靈丹妙藥,還是種十分時髦的靈丹妙藥,後來人們卻又開始強烈地抵制它(或許這種反應不足為奇)。關於選擇性血清素再攝取抑制劑 (SSRI) 是否會增加某些人,特別是青少年的自殺事件或自殺傾向,精神科醫生提出了嚴厲的質問。目前尚無研究證實兩者之間存在必然的關聯,但是這並沒有打消某些著名的懷疑論者的疑慮。有人覺得百憂解可以救命,其他使用者則認為它剝奪了人正常的生理感覺。百憂解的一個常見的副作用是喪失性欲。還有一些作家和藝術家聲稱,雖然百憂解將他們從抑鬱症的魔爪之下解脫了出來,卻也讓他們精神恍惚。作者提出:“如果百憂解早在上個世紀就問世的話,那麼波德賴爾 (Baudelaire) 的“憂鬱”、愛德格•愛倫•坡 (Edgar Allan Poe) 的浪漫主義情懷、西維亞•普拉斯 (Sylvia Plath) 的詩歌、以及那麼多其他詩人的哀歎,所有那些有靈魂的作品都將遭到扼殺。”
- 若醫師漏開藥物給心臟病患者,很有可能會因為疏漏而遭告控告;但藥物所造成的副作用,醫師卻都不用受到任何懲罰。受到醫療傷害的是病人,從醫療當中獲利的則是醫生。應該去治療的是嚴重的疾病,而忽略其他不是很嚴重與迫切的狀況
- 按照生理學的原理,節食以後,人的身體會相應改變處理食物的方式,通過拒絕釋放脂肪、減慢新陳代謝的速度和強烈的進食慾望,阻止你變得太胖或太瘦。更要命的是,人體本來是一個反脆弱系統,節食的確能讓身體暫時變瘦,但身體的反脆弱機制是越缺少什麼,你就會越用更大力量去吸收什麼。當攝入越少,身體就會犧牲一些機能,來維持基本生存,這不僅沒有達到消耗大於攝入的目的,反而影響了健康,甚至影響壽命。
- 人體細胞有三個敵人:發炎、氧化應激反應和胰島素抵抗。對付第一個敵人,也可以吃一些能讓身體不發炎的食物,比如:魚類、牛奶、有機雞蛋之類。維生素C和維生素E能對付第二個敵人,你可以從水果、胡蘿蔔、西紅柿、土豆和一些綠葉蔬菜中獲得。對付胰島素抵抗,最關鍵的就是要少吃糖,特別可樂等含糖飲料,應該堅決抵制。另外,紅肉(哺乳動物的肉)、香腸、火腿、麵包等都應該少吃,而植物纖維、全麥、堅果、豆類、海帶等則是比較安全的,這些是老生常談的東西了,但確實很重要。
- Attribute problem (歸因問題) 是指人們常將成功歸因於自己的能力,失敗則歸咎壞運氣,這樣的歸因問題常見於股票經紀人、醫生、公司主管等
- 醫生看到腫瘤,沒辦法不做有害的事,例如在放射、化學治療或兩者都做之後進行手術—這些,對人體的傷害大於腫瘤。心生恐慌的醫生和病人很容易跨越一個平衡點;去治療不會使你死亡的腫瘤,會使你的生命縮短,因為化學治療是有毒的。
- 將否定法用在醫藥上,會有許多隱性珍寶。舉例來說,勸人不要抽菸似乎是六十年來最大的醫藥貢獻。德魯恩•伯奇(Druin Burch)在《服藥》(Taking the Medicine)一書中寫道:「吸菸的有害影響,大約等於戰後以來發展出的每一種醫療干預合起來的好處……戒菸帶來的好處,高於我們能夠治療每一種可能的癌症。」
- 肯定後件(Affirming the consequent),是一種形式謬誤,以下範例做出錯誤的結論:如果有火災,就會有濃煙;有濃煙,因此,有火災。但是,有濃煙未必是因為發生了火災。比如說,火力發電廠可能就會產生濃煙。就算因為癌症而早死的所有人都長出惡性腫瘤,並不表示所有的惡性腫瘤都會使人因為癌症而死。大部分同樣聰明的人,不會因為所有的克里特島人(Cretans)都是騙子這個事實,就推論說所有的騙子都是克里特島人,或者從所有的銀行家都貪腐,推論所有貪腐的人都是銀行家。
- 『追求幸福』不等於『避免不幸福』,你反倒該清楚了解有那些事情讓你感到不快樂 (如長時間通勤、壞味道、身體疼痛等),解決讓你感到不快樂的事物,才是追求幸福的方式
- 減法法則:我們知道錯誤的事物遠多於正確的事情。知道不做什麼,少即是多。並且根據林迪效應,也要避免新事物狂熱。隨著歷史和實踐湧現出來的舊事物往往是反脆弱的。
- 「安慰劑效應」(placebo effect) 指的是,病人雖然獲得無效的治療,但卻「預料」或「相信」治療有效,而讓病患症狀得到舒緩的現象。一個性質完全相反的效應是反安慰劑效應 (nocebo effect):病人不相信治療有效,可能會令病情惡化。
- second order effect: 指的是『訊息的訊息比訊息重要』。女人是人際關係中 second order 的專家。她們都知道,問題不是你說什麼,問題是你說這句的用意。
- 自噬作用 (autophagy) 是普遍存在於大部分真核細胞中的一種現象,是溶酶體對自身結構的吞噬降解,它是細胞內的再循環系統 (recycling system)。自噬作用主要是清除降解細胞內受損傷的細胞結構、衰老的細胞器、以及不再需要的生物大分子等。自噬作用在消化的同時,也為細胞內細胞器的構建提供原料,即細胞結構的再循環。因此,溶酶體相當於細胞內清道夫。如細胞面臨營養、環境不好時會進行自體吞噬,細胞內的部分胞器、大型損傷的蛋白進行自體吞噬分解成胜肽鏈 (peptides),細胞可以回收再利用,進而降低能量消耗,若營養還是不足細胞最終仍會死亡;又如當腫瘤細胞接受到放射線、藥物的傷害,他會進行自體吞噬(autophagy),降低外來攻擊所造成的傷害,亦是腫瘤細胞存活的一種機制。
- 現代社會反而是一群汲汲營營的中產階級與行政官僚在當家,社會因為懦弱的中產階級與沒有骨氣的政治人物而變得脆弱,大家都在作短多長空的表面工夫。
- 除非你願意為你所珍惜重視的事物付出代價,否則它一文不值。願意付出代價才是真正的勇氣。
- 所謂的氣度 (megalopsychon) 是:願意承擔風險、有尊嚴地面對自己的命運,不會做出貶低自己的任何事情。如果你不承擔風險,那麼你無法成就任何使你自己偉大的事物。
- 英雄與代理問題 (agency problem) 的差異,作者認為古代英雄往往是自己也承受了同樣的下行 (downside) 風險和上行 (upside) 獲利空間。但現代許許多多政治人物,經濟學家,企管顧問,教授….等,都是用理論去讓別人承擔下行風險,自己得到上行獲利。而解決方法,是確保提供方法的人,同樣也承擔了風險。 這點在台灣也不難理解,不管是政府推行的干預計畫,或是股市上每每被套牢的股民,美國也同樣如此。
- 我們應該建立備餘 (redundancy) 與安全邊際 (margin of safety),避免最佳化 (optimization),減輕我們對風險的敏感度
- 沉默的好人是邪惡的同謀;換言之,沒有積極阻止犯罪的人,也是共犯。
- 許多財經名嘴就是典型的提出不負責任的預測,導致無辜的觀眾聽信並投資,遭受下行 (downside) 投資損失,財經名嘴卻獲得上行 (upside) 獲利 (如通告費),完全不須因為預測失準而受到懲罰
- 股票市場是有史以來,最邪惡、規模最大的風險轉移,造成投資人與退休人士龐大的損失,而讓企業經理人更富有。銀行讓投資人承擔下檔利益,自己享受上檔利益。股票市場的波動越利害,經理人與券商獲得的利益越大,投資人的風險則越大。
- 別問任何人他們的投資意見、預測或推薦。只要問他們的投資組合中有甚麼或沒有什麼即可。如同不要問醫生你應該怎麼做。問他如果置身於和你相同情況,他會怎麼做。兩者的差異會令你大吃一驚。
- 脆弱的情況中,一個人只能賺很少,卻會賠很多錢;在反脆弱的情況中,則會賺大錢,但賠小錢。所以反脆弱可以賠很長的時間,但損傷不大,只要後來做對那一次;對脆弱來說,單單一次損失就會讓人一蹶不振。
- 冤大頭試著贏得爭論,非冤大頭則試著贏 (suckers try to win arguments, nonsuckers try to win)
- 對大自然來說,意見和預測都不重要;重要的是生存。
- 就生存而言,同樣是犯錯,把一隻熊當成是石頭 (這個錯誤會讓人喪命) 或把石頭當成一隻熊 (這個錯誤只會讓人虛驚一場)。長久下來,第二種大驚小怪、過度反應的人才能夠生存;犯第一種錯誤的人則會離開基因庫 (gene pool)。
- 人對好事的感受,不如對壞事感受的強烈,所以我們容易變成壞情緒的俘虜。
- 由於成功會帶來不對稱,成功的人之後可能失去的, 遠多於得到的,因此會顯得脆弱,例如富有的人失去財富時的痛苦遠高於得到額外財富的喜悅。因此你應該:
- 每天早上假設最糟的狀況已經發生,所以當天接下來發生的每一件事情都是賺到的。
- 心理上調到需要面對最糟狀況的方法優點多過治療,去冒最糟情況十分清楚,下檔損失有限且已知的某種風險
- 在有壓力的情況下,規模會讓你受傷害;在艱難的情況下,規模大並非好事。隨著規模的進一步增大,其代價會非線性地增加。在外界衝擊面前,大型動物比小型動物表現得更脆弱。
- Champagne socialists(香檳社會主義者):此為英國的用語,指的是自稱社會主義者,但又大啖美食、開名車,違背社會主義的價值。美國人稱他們為 Limousine liberals(豪華轎車自由主義者),法國人一樣稱他們為 Gauche caviar(魚子醬左派份子),但不論如何,這些都是指那些富裕的左派份子。儘管他們不會承認,但不過事實上就是,他們同時愛著勞力士和馬克思主義。當我們需要一個人,我們在心裡假設她是我們的人,是最了解我們、最知道我們的訴求、甚至也和我們一起有過相同的喜怒哀樂的人,其實我們不過是在這個人身上投射了自己的希望。我們確實應該持有希望,甚至作為人類我們存在這個世界上很大程度上的意義是:希望。但我們最好別把希望變成指望,指望一個人,指望她為我們說些什麼,指望她為我們寫些什麼,指望她為我們做些什麼.....那幾乎是不可能的,所以還是指望自己吧!
- 基金公司與主動經理人鼓吹主動投資的好處,但落後指數績效,後果由投資人承擔,基金公司與經理人繼續坐享他們的高額收入。 許多大師、專欄作家不斷對市場未來提出預測。結果預測錯了怎麼辦? 不會怎樣,因為不良後果是由相信這些預測的投資人承擔。這些專家還是會繼續提供預測的。 這種狀況在英文叫做:”No skin in the game.” 。遊戲的輸贏跟他根本沒關係,於是他們就繼續在那邊大放厥詞。
- 漢摩拉比法典曾提到: 假如一個工匠建的房子倒了,造成屋主死亡,那麼這個工匠會被處死。假如房子倒了,壓死屋主的兒子,那麼工匠的兒子會被處死。 這就是典型的以眼還眼哲學。 當我們現代人取笑其”野蠻”之處時,卻常忽略,該法條強迫參與,強迫你也有「 Skin in the game」 的智慧。 重點其實不在於罰則,而是在於它帶來”對稱性”。出事,不是別人付出代價,自己也有對等代價,重點在於它的嚇阻作用。所以,一個不投資自己基金的主動型基金經理人,一個不住自己建案的建設公司老闆,一個不照自己預測投資的預言大師,你知道該怎麼做了。
- 現代社會,勇氣代表為自己的意見挺身而出,不是只有意見而已,而是自己真的有照這個意見去做。假如錯了,自己也會付出代價。現在多的是,只有意見,但自己根本不敢照著做的反英雄 (Inverse hero),我們還給予他們崇高的社會地位。Inverse hero 是比膽小、怯懦更無用的人,他們大膽嘗試,然後由客戶付出代價。 反英雄不是膽小、怯懦的人。他可以很大膽、很勇敢,但是由別人承擔他犯錯的代價。小心不要成為這種人,也不要成為這種人的犧牲品。
- 銀行業有個令人無法接受的現象:銀行賠錢,但是銀行的經理人一樣獲得豐厚的報酬。納稅人吸收了 downside,銀行家獲得 upside。銀行家是 antifragile,而你這位納稅人則是 fragile。整個社會因為銀行大到不能倒而負擔了銀行家的鉅額損失,但社會並沒從中獲得任何回報,銀行家將 fragility 轉移給你 (transfer of fragility),讓自己變成 antifragile
- 商業世界的問題是,其運作是透過加法而非減法:如果你盡量少碰糖,藥商就賺不到錢;如果你決定規律地在戶外運動、跑步、打球,健身器材製造商無法從你身上獲得好處;如果你不頻繁交易,你的股票經紀人無法從你的交易抽傭
- 絕對不要相信不自由 (為利益所驅使) 的人所說的話(打領帶的人往往就是這些為利益所驅使、不可相信的奴隸)
- 自由的人才能夠有自己的意見,懦弱是後天造就與社會化造成的,這些人不管多麼富有、多麼獨立,只要考量他人觀感,他們依然懦弱。
- 法律規定越複雜,社會網絡越官僚,就有越多深諳系統漏洞和缺陷的主管官員從中受益,因為他的主管優勢將是其專業知識的凸性函數。這是一種特權,是以犧牲別人為代價獲得的不對稱性。這種特權正在整個經濟中蔓延;豐田汽車公司就曾聘請前美國主管官員,利用他們的“專業知識”來處理汽車缺陷調查案。
- 法律規定越複雜,業內人士越容易找到套利的機會。這裡,我們又可以看出啟發法的優勢。2300頁的法規在我看來抵不上幾條《漢謨拉比法典》。厚厚的法規對前主管官員來說簡直就是一座金礦,他們有足夠的動機贊成複雜的法律法規。我們再次看到,內部人是“少即是多”原則的敵人。
- 在一個複雜的系統中,法律法規的字面意思與實質意思之間的差異很難讓人辨識。也就是說,技術性的、複雜的、非線性的環境比只涉及少數變數的線性環境更容易受人操縱。法律和道德之間的缺口,同樣如此。
- 你應該更重視提供不利於自己的證據的證人和意見。例如,提倡饑餓療法和通過否定法治療糖尿病的大型製藥公司的藥劑師或高管,要比支持大量吃藥的藥劑師或高管可信得多。
- 大數據的悲劇。變數越多,“老練”的研究員手中的顯著相關性越多。虛假相關性的增長比信息增長得更快,數據因而呈現出非線性(凸性)。數據只能真正提供以『否定法』界定的知識——它可以有效地用於揭穿,而非確認某種觀點。
- 在這個世界上最可以使用“其他人都這麼認為”作為論點的最後一個地方是科學:科學應該讓論點本身站得住腳,被經驗或數學證明為錯誤的話點就是毫無疑問地錯了,即使有100個“專家”或3萬億條反對意見來支持它也沒有用。而且,用“其他人”來支持自己的論點其實意味著這個人——或組成“其他人”的整體——很無用而已。
- 這世間一切的事物都會從波動性中獲得收益或遭受損失。脆弱性就是波動性和不確定性帶來的損失。放在桌子上的玻璃杯是很怕波動性的。
- 時間是具有波動性的。教育,從塑造性格和個性、獲取真正知識的意義上說,是喜歡無序的;貼標籤式的教育和教育者則對無序深惡痛絶。有些事情會因為錯誤而失敗,有些則不會。一些理論會土崩瓦解,而其他理論則不會。創新恰恰是從不確定性中獲益的東西;而有的人還會坐等不確定性,並用它作為原料,就像我們的獵人祖先。
- 我們可能永遠不會瞭解 x,但我們可以考慮 x 的風險,用槓鈴模式 (barbell strategy) 來解決問題;即使 x 仍然大大超出我們的理解,我們也可以控制 x 的函數,也就是 f(x)。我們可以不斷地改變 f(x),直到我們用一種機制讓我們對其感到放心。這種機制就是凸性轉換 (convex transformation),是槓鈴模式的一個比較時髦的名字。
- 玻璃杯是死的東西,活的東西才喜歡波動性。驗證你是否活著的最好方式,就是查驗你是否喜歡變化。請記住,如果不覺得饑餓,山珍野味也會食之無味;如果沒有辛勤付出,得到的結果將毫無意義;同樣的,沒有經歷過傷痛,便不懂得歡樂;沒有經歷過磨難,信念就不會堅固;被剝奪了個人風險,合乎道德的生活自然也沒有意義。
Total Pageviews
2019/03/01
[閱讀筆記] Antifragile: Things That Gain from Disorder (10/10)
Labels:
Reading
2019/02/28
2019/02/27
2019/02/26
2019/02/15
[Java] How to convert seconds to minutes?
Problem
How to convert seconds to minutes in Java ?
For example, 230 seconds should convert to 3 minutes 50 seconds.
How-To
Here has sample code:
How to convert seconds to minutes in Java ?
For example, 230 seconds should convert to 3 minutes 50 seconds.
How-To
Here has sample code:
package albert.test; import java.util.concurrent.TimeUnit; public class TimeUtils { public static void main(String[] args) { System.out.println(TimeUtils.toMinutes(230)); } public static String toMinutes(long second) { long mm = TimeUnit.SECONDS.toMinutes(second); long ss = TimeUnit.SECONDS.toSeconds(second) - (mm * 60); String str = "%d 分 %d 秒"; return String.format(str, mm, ss); } }
Labels:
Java
2019/02/14
[Sybase] How to get the difference between two days
Problem
I have a datetime column in Sybase table, if I would like to calculate the number of second between this column and current datetime. How to do it?
How-To
Using datediff to calculate the number of seconds between two date.
The syntax and parameters are:
The SQL statement is as bellows:
Reference
http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.infocenter.dc36271.1570/html/blocks/X47295.htm
I have a datetime column in Sybase table, if I would like to calculate the number of second between this column and current datetime. How to do it?
How-To
Using datediff to calculate the number of seconds between two date.
The syntax and parameters are:
The SQL statement is as bellows:
SELECT DATA_TIME, datediff(ss, DATA_TIME, getdate()) as DIFF FROM TEST;
Reference
http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.infocenter.dc36271.1570/html/blocks/X47295.htm
Labels:
Database
2019/02/13
[Java] How to compress TIF file with multiple pages?
Problem
How to compress TIF file with multiple pages in Java?
How-To
Add dependency in your pom.xml
Here has sample code:
How to compress TIF file with multiple pages in Java?
How-To
Add dependency in your pom.xml
<dependency> <groupId>com.github.jai-imageio</groupId> <artifactId>jai-imageio-core</artifactId> <version>1.3.1</version> </dependency>
Here has sample code:
package demo.util; import java.awt.image.BufferedImage; import java.io.BufferedInputStream; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import javax.imageio.IIOImage; import javax.imageio.ImageIO; import javax.imageio.ImageReader; import javax.imageio.ImageWriteParam; import javax.imageio.ImageWriter; import javax.imageio.stream.ImageInputStream; import javax.imageio.stream.ImageOutputStream; import com.github.jaiimageio.impl.plugins.tiff.TIFFImageReaderSpi; import com.github.jaiimageio.impl.plugins.tiff.TIFFImageWriterSpi; import lombok.extern.slf4j.Slf4j; /* * tif 壓縮程式 */ @Slf4j public class TiffCompression { /** * 用 Deflate 進行 TIF 壓縮. * * @param source * 來源 TIF 檔 * @param target * 壓縮後的 TIF 檔 * @throws IOException */ public static void compress(File source, File target) throws IOException { ImageIO.scanForPlugins(); ImageWriter writer = null; try (InputStream fis = new BufferedInputStream(new FileInputStream(source)); ImageInputStream iis = ImageIO.createImageInputStream(fis); ImageOutputStream targetTif = ImageIO.createImageOutputStream(target);) { // tif 來源檔 TIFFImageReaderSpi readSpi = new TIFFImageReaderSpi(); ImageReader reader = readSpi.createReaderInstance(); reader.setInput(iis); // tif 目的檔 TIFFImageWriterSpi tiffspi = new TIFFImageWriterSpi(); writer = tiffspi.createWriterInstance(); writer.setOutput(targetTif); // 取得 tif 分頁 Integer pageSize = reader.getNumImages(true); BufferedImage image[] = new BufferedImage[pageSize]; // 設定壓縮參數 ImageWriteParam param = writer.getDefaultWriteParam(); param.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); // 有試過 CCITT T.4, CCITT T.6, PackBits, Deflate 與 LZW,Deflate 壓縮比最佳 param.setCompressionType("Deflate"); // 逐頁讀出檔案,並寫入目的地 for (int i = 0; i < pageSize; i++) { image[i] = reader.read(i); IIOImage iioImage = new IIOImage(image[i], null, null); if (i == 0) { writer.write(null, iioImage, param); } else { writer.writeInsert(-1, iioImage, param); } } } catch (IOException e) { throw new IOException("TIF 壓縮失敗", e); } finally { if (writer != null) { writer.dispose(); } } } }
Labels:
Java
2019/02/12
[Spring] java.security.InvalidAlgorithmParameterException: the trustAnchors parameter must be non-empty
Problem
When I try to call web service via WebServiceTemplate, which provided by Spring framework. It throw the following exception:
The code snippet is as following:
How-To
Owing to the web service url is https, so you need to disable SSL certificate checking.
You need create an UnTrustworthyTrustManager:
And set UnTrustworthyTrustManager into MessageSender
When I try to call web service via WebServiceTemplate, which provided by Spring framework. It throw the following exception:
java.lang.RuntimeException: Unexpected error: java.security.InvalidAlgorithmParameterException: the trustAnchors parameter must be non-empty; nested exception is javax.net.ssl.SSLException: java.lang.RuntimeException: Unexpected error: java.security.InvalidAlgorithmParameterException: the trustAnchors parameter must be non-empty at org.springframework.ws.client.core.WebServiceTemplate.sendAndReceive(WebServiceTemplate.java:561) at org.springframework.ws.client.core.WebServiceTemplate.marshalSendAndReceive(WebServiceTemplate.java:390) at org.springframework.ws.client.core.WebServiceTemplate.marshalSendAndReceive(WebServiceTemplate.java:378)
The code snippet is as following:
package demo.service.client; import javax.net.ssl.TrustManager; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Component; import org.springframework.ws.client.core.WebServiceTemplate; import demo.dto.status; import demo.dto.mapper.StatusMapper; import demo.ws.bind.status.SendStatusRequest; import demo.ws.bind.status.SendStatusResponse; import lombok.extern.slf4j.Slf4j; @Slf4j @Component public class StatusClient { @Autowired private WebServiceTemplate wsTemplate; @Value("${webservices.host}") private String host; @Value("${webservices.url.status}") private String url; @Autowired private StatusMapper mapper; public SendStatusResponse sendData(Status entity) { SendStatusRequest request = new SendStatusRequest(); request.setStatusDto(mapper.toDto(entity)); return (SendStatusResponse) wsTemplate.marshalSendAndReceive(host + url, request); } }
How-To
Owing to the web service url is https, so you need to disable SSL certificate checking.
You need create an UnTrustworthyTrustManager:
package demo.service.client; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import javax.net.ssl.X509TrustManager; public class UnTrustworthyTrustManager implements X509TrustManager { @Override public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { // TODO Auto-generated method stub } @Override public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { // TODO Auto-generated method stub } @Override public X509Certificate[] getAcceptedIssuers() { // TODO Auto-generated method stub return null; } }
And set UnTrustworthyTrustManager into MessageSender
package demo.service.client; import javax.net.ssl.TrustManager; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Component; import org.springframework.ws.client.core.WebServiceTemplate; import org.springframework.ws.transport.http.HttpsUrlConnectionMessageSender; import demo.dto.status; import demo.dto.mapper.StatusMapper; import demo.ws.bind.status.SendStatusRequest; import demo.ws.bind.status.SendStatusResponse; import lombok.extern.slf4j.Slf4j; @Slf4j @Component public class StatusClient { @Autowired private WebServiceTemplate wsTemplate; @Value("${webservices.host}") private String host; @Value("${webservices.url.status}") private String url; @Autowired private StatusMapper mapper; public SendStatusResponse sendData(Status entity) { HttpsUrlConnectionMessageSender sender = new HttpsUrlConnectionMessageSender(); sender.setTrustManagers(new TrustManager[] { new UnTrustworthyTrustManager() }); wsTemplate.setMessageSender(sender); SendStatusRequest request = new SendStatusRequest(); request.setStatusDto(mapper.toDto(entity)); return (SendStatusResponse) wsTemplate.marshalSendAndReceive(host + url, request); } }
Labels:
Spring
2019/02/11
[Java] BEA-380001-Internal Server Error
Scenario
How-To
The root cause is unknown. But comparing with workable client code with non-workable client code, there has one difference in package-info.java.
The package-info.java in workable client code is:
The package-info.java in non-workable client code is:
Therefore, as I add annotation above package, the problem had been resolved.
How-To
The root cause is unknown. But comparing with workable client code with non-workable client code, there has one difference in package-info.java.
The package-info.java in workable client code is:
@javax.xml.bind.annotation.XmlSchema(namespace = "http://test.com", elementFormDefault = javax.xml.bind.annotation.XmlNsForm.QUALIFIED) package demo.ws.bind.test1;
The package-info.java in non-workable client code is:
package demo.ws.bind.test2;
Therefore, as I add annotation above package, the problem had been resolved.
Labels:
Java
2019/02/10
[Tool] [SoapUI] How to setup SOAP Web Service HTTP Basic Authentication
Scenario
How-To
Here has two steps to set up HTTP Basic Authentication :
Step 1. Invoke context menu, and choose "Show Interface Viewer"
Step 2. Fill in user name and password.
How-To
Here has two steps to set up HTTP Basic Authentication :
Step 1. Invoke context menu, and choose "Show Interface Viewer"
Step 2. Fill in user name and password.
Labels:
Tools
2019/02/09
[SoapUI] A class/interface with the same name "xxxx" is already in use. Use a class customization to resolve this conflict.
Problem
When I try to generate SOAP web service client code via SoapUI, I get naming conflict exception:
How-To
We can add customized argument in SoapUI to automatically resolve naming conflicts without requiring the use of binding customizations.
Reference
[1] http://cxf.apache.org/docs/wsdl-to-java.html
When I try to generate SOAP web service client code via SoapUI, I get naming conflict exception:
[ERROR] A class/interface with the same name "xxxx" is already in use. Use a class customization to resolve this conflict.
How-To
We can add customized argument in SoapUI to automatically resolve naming conflicts without requiring the use of binding customizations.
Reference
[1] http://cxf.apache.org/docs/wsdl-to-java.html
Subscribe to:
Posts (Atom)