日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > java >内容正文

java

java高性能序列化_Java最佳实践–高性能序列化

發布時間:2023/12/3 java 31 豆豆
生活随笔 收集整理的這篇文章主要介紹了 java高性能序列化_Java最佳实践–高性能序列化 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

java高性能序列化

在使用Java編程語言時,我們將繼續討論與建議的實踐有關的系列文章,我們將討論并演示如何將對象序列化用于高性能應用程序。

所有討論的主題均基于用例,這些用例源于電信行業關鍵任務超高性能生產系統的開發。

在閱讀本文的每個部分之前,強烈建議您參考相關的Java API文檔以獲取詳細信息和代碼示例。

所有測試均針對具有以下特征的Sony Vaio進行:

  • 系統:openSUSE 11.1(x86_64)
  • 處理器(CPU):Intel(R)Core(TM)2 Duo CPU T6670 @ 2.20GHz
  • 處理器速度:1,200.00 MHz
  • 總內存(RAM):2.8 GB
  • Java:OpenJDK 1.6.0_0 64位

應用以下測試配置:

  • 并發工人線程:200
  • 每個工作人員重復測試的線程數:1000
  • 整體測試次數:100

高性能序列化

序列化是將對象轉換為字節流的過程。 然后可以通過套接字發送該流,將其存儲到文件和/或數據庫中,或者直接按原樣對其進行操作。 在本文中,我們不打算對序列化機制進行深入的描述,有許多文章提供了這種信息。 這里將討論的是我們利用序列化以實現高性能結果的主張。

序列化的三個主要性能問題是:

  • 序列化是一種遞歸算法。 從單個對象開始,還可以對通過實例變量可以從該對象訪問的所有對象進行序列化。 默認行為很容易導致不必要的序列化開銷
  • 序列化和反序列化都需要序列化機制來發現有關其序列化實例的信息。 使用默認的序列化機制,將使用反射來發現所有字段值。 此外,如果您沒有明確設置“ serialVersionUID”類屬性,則序列化機制必須對其進行計算。 這涉及遍歷所有字段和方法以生成哈希。 上述過程可能會很慢
  • 使用默認的序列化機制,所有序列化類描述信息都包含在流中,例如:
    • 所有可序列化超類的描述
    • 類本身的描述
    • 與類的特定實例關聯的實例數據

要解決上述性能問題,可以改用外部化。 這兩種方法之間的主要區別在于,序列化將所有可序列化超類的類描述以及與該實例相關聯的信息(當被視為每個單獨的超類的實例)一起寫出。 另一方面,外部化會寫出類的標識(類的名稱和適當的“ serialVersionUID”類屬性)以及超類結構以及有關類層次結構的所有信息。 換句話說,它存儲所有元數據,但僅寫出本地實例信息。 簡而言之,外部化幾乎消除了序列化機制使用的所有反射調用,使您可以完全控制編組和解組算法,從而顯著提高性能。

當然,外部化效率是有代價的。 由于從類定義中自動提取了元數據,因此默認的序列化機制可適應應用程序更改。 另一方面,外部化不是很靈活,需要您在更改類定義時重寫編組和解組代碼。

以下是有關如何將外部化用于高性能應用程序的簡短演示。 我們將從提供“ Employee”對象開始執行序列化和反序列化操作。 將使用兩種類型的“ Employee”對象。 一種適合標準序列化操作,另一種經過修改以便可以外部化。

以下是“雇員”對象的第一種味道:

package com.javacodegeeks.test;import java.io.Serializable; import java.util.Date; import java.util.List;public class Employee implements Serializable {private static final long serialVersionUID = 3657773293974543890L;private String firstName;private String lastName;private String socialSecurityNumber;private String department;private String position;private Date hireDate;private Double salary;private Employee supervisor;private List<string> phoneNumbers;public Employee() {}public Employee(String firstName, String lastName,String socialSecurityNumber, String department, String position,Date hireDate, Double salary) {this.firstName = firstName;this.lastName = lastName;this.socialSecurityNumber = socialSecurityNumber;this.department = department;this.position = position;this.hireDate = hireDate;this.salary = salary;}public String getFirstName() {return firstName;}public void setFirstName(String firstName) {this.firstName = firstName;}public String getLastName() {return lastName;}public void setLastName(String lastName) {this.lastName = lastName;}public String getSocialSecurityNumber() {return socialSecurityNumber;}public void setSocialSecurityNumber(String socialSecurityNumber) {this.socialSecurityNumber = socialSecurityNumber;}public String getDepartment() {return department;}public void setDepartment(String department) {this.department = department;}public String getPosition() {return position;}public void setPosition(String position) {this.position = position;}public Date getHireDate() {return hireDate;}public void setHireDate(Date hireDate) {this.hireDate = hireDate;}public Double getSalary() {return salary;}public void setSalary(Double salary) {this.salary = salary;}public Employee getSupervisor() {return supervisor;}public void setSupervisor(Employee supervisor) {this.supervisor = supervisor;}public List<string> getPhoneNumbers() {return phoneNumbers;}public void setPhoneNumbers(List<string> phoneNumbers) {this.phoneNumbers = phoneNumbers;}}

這里要注意的事情:

  • 我們假定以下字段是必填字段:
    • “名字”
    • “姓”
    • “社會安全號碼”
    • “部門”
    • “位置”
    • “雇用日期”
    • “薪水”

以下是“雇員”對象的第二種風味:

package com.javacodegeeks.test;import java.io.Externalizable; import java.io.IOException; import java.io.ObjectInput; import java.io.ObjectOutput; import java.util.Arrays; import java.util.Date; import java.util.List;public class Employee implements Externalizable {private String firstName;private String lastName;private String socialSecurityNumber;private String department;private String position;private Date hireDate;private Double salary;private Employee supervisor;private List<string> phoneNumbers;public Employee() {}public Employee(String firstName, String lastName,String socialSecurityNumber, String department, String position,Date hireDate, Double salary) {this.firstName = firstName;this.lastName = lastName;this.socialSecurityNumber = socialSecurityNumber;this.department = department;this.position = position;this.hireDate = hireDate;this.salary = salary;}public String getFirstName() {return firstName;}public void setFirstName(String firstName) {this.firstName = firstName;}public String getLastName() {return lastName;}public void setLastName(String lastName) {this.lastName = lastName;}public String getSocialSecurityNumber() {return socialSecurityNumber;}public void setSocialSecurityNumber(String socialSecurityNumber) {this.socialSecurityNumber = socialSecurityNumber;}public String getDepartment() {return department;}public void setDepartment(String department) {this.department = department;}public String getPosition() {return position;}public void setPosition(String position) {this.position = position;}public Date getHireDate() {return hireDate;}public void setHireDate(Date hireDate) {this.hireDate = hireDate;}public Double getSalary() {return salary;}public void setSalary(Double salary) {this.salary = salary;}public Employee getSupervisor() {return supervisor;}public void setSupervisor(Employee supervisor) {this.supervisor = supervisor;}public List<string> getPhoneNumbers() {return phoneNumbers;}public void setPhoneNumbers(List<string> phoneNumbers) {this.phoneNumbers = phoneNumbers;}public void readExternal(ObjectInput objectInput) throws IOException,ClassNotFoundException {this.firstName = objectInput.readUTF();this.lastName = objectInput.readUTF();this.socialSecurityNumber = objectInput.readUTF();this.department = objectInput.readUTF();this.position = objectInput.readUTF();this.hireDate = new Date(objectInput.readLong());this.salary = objectInput.readDouble();int attributeCount = objectInput.read();byte[] attributes = new byte[attributeCount];objectInput.readFully(attributes);for (int i = 0; i < attributeCount; i++) {byte attribute = attributes[i];switch (attribute) {case (byte) 0:this.supervisor = (Employee) objectInput.readObject();break;case (byte) 1:this.phoneNumbers = Arrays.asList(objectInput.readUTF().split(";"));break;}}}public void writeExternal(ObjectOutput objectOutput) throws IOException {objectOutput.writeUTF(firstName);objectOutput.writeUTF(lastName);objectOutput.writeUTF(socialSecurityNumber);objectOutput.writeUTF(department);objectOutput.writeUTF(position);objectOutput.writeLong(hireDate.getTime());objectOutput.writeDouble(salary);byte[] attributeFlags = new byte[2];int attributeCount = 0;if (supervisor != null) {attributeFlags[0] = (byte) 1;attributeCount++;}if (phoneNumbers != null && !phoneNumbers.isEmpty()) {attributeFlags[1] = (byte) 1;attributeCount++;}objectOutput.write(attributeCount);byte[] attributes = new byte[attributeCount];int j = attributeCount;for (int i = 0; i < 2; i++)if (attributeFlags[i] == (byte) 1) {j--;attributes[j] = (byte) i;}objectOutput.write(attributes);for (int i = 0; i < attributeCount; i++) {byte attribute = attributes[i];switch (attribute) {case (byte) 0:objectOutput.writeObject(supervisor);break;case (byte) 1:StringBuilder rowPhoneNumbers = new StringBuilder();for(int k = 0; k < phoneNumbers.size(); k++)rowPhoneNumbers.append(phoneNumbers.get(k) + ";");rowPhoneNumbers.deleteCharAt(rowPhoneNumbers.lastIndexOf(";"));objectOutput.writeUTF(rowPhoneNumbers.toString());break;}}} }

這里要注意的事情:

  • 我們實現了用于編組“雇員”對象的“ writeExternal”方法。 所有必填字段都寫入流
  • 對于“ hireDate”字段,我們僅寫入此Date對象表示的毫秒數。 假設demarshaller將使用與marshaller相同的時區,那么毫秒值就是我們要正確反序列化“ hireDate”字段所需的所有信息。 請記住,我們可以使用“ objectOutput.writeObject(hireDate)”操作來序列化整個“ hireDate”對象。 在這種情況下,默認的序列化機制將導致結果流的速度下降和大小增加
  • 所有非強制性字段(“ supervisor”和“ phoneNumbers”)只有在具有實際值(非null)時才被寫入流中。 為了實現此功能,我們使用“ attributeFlags”和“ attributes”字節數組。 “ attributeFlags”數組的每個位置代表一個非強制性字段,并保留一個“標記”,指示特定字段是否具有值。 我們檢查每個非必填字段,并使用相應的標記填充“ attributeFlags”字節數組。 “屬性”字節數組指示必須通過“位置”寫入流中的實際非必需字段。 例如,如果“ supervisor”和“ phoneNumbers”非必填字段均具有實際值,則“ attributeFlags”字節數組應為[1,1],而“ attributes”字節數組應為[0,1]。 如果只有“ phoneNumbers”非必需字段具有非空值,則“ attributeFlags”字節數組應為[0,1],而“ attributes”字節數組應為[1]。 通過使用上述算法,我們可以為生成的流實現最小的尺寸占用。 為了正確地反序列化“ Employee”對象的非必需參數,我們必須僅將以下信息寫入流:
    • 將要寫入的非強制性參數的總數(又稱“屬性”字節數組大小-供編組者解析)
    • “屬性”字節數組(供編組員正確分配字段值)
    • 實際非強制性參數值
  • 對于“ phoneNumbers”字段,我們構造并將其內容的String表示形式寫入流中。 或者,我們可以使用“ objectOutput.writeObject(phoneNumbers)”操作來序列化整個“ phoneNumbers”對象。 在這種情況下,默認的序列化機制將導致結果流的速度下降和大小增加
  • 我們實現了“ readExternal”方法來對“ Employee”對象進行編組。 所有必填字段都將寫入流中。 對于非必填字段,demarshaller根據上述協議分配適當的字段值

對于序列化和反序列化過程,我們使用了以下四個功能。 這些功能有兩種形式。 第一對適用于序列化和反序列化Externalizable對象實例,而第二對適用于序列化和反序列化Serializable對象實例。

public static byte[][] serializeObject(Externalizable object) throws Exception {ByteArrayOutputStream baos = null;ObjectOutputStream oos = null;byte[][] res = new byte[2][];try {baos = new ByteArrayOutputStream();oos = new ObjectOutputStream(baos);object.writeExternal(oos);oos.flush();res[0] = object.getClass().getName().getBytes();res[1] = baos.toByteArray();} catch (Exception ex) {throw ex;} finally {try {if(oos != null)oos.close();} catch (Exception e) {e.printStackTrace();}}return res;}public static Externalizable deserializeObject(byte[][] rowObject) throws Exception {ObjectInputStream ois = null;String objectClassName = null;Externalizable res = null;try {objectClassName = new String(rowObject[0]);byte[] objectBytes = rowObject[1];ois = new ObjectInputStream(new ByteArrayInputStream(objectBytes));Class objectClass = Class.forName(objectClassName);res = (Externalizable) objectClass.newInstance();res.readExternal(ois);} catch (Exception ex) {throw ex;} finally {try {if(ois != null)ois.close();} catch (Exception e) {e.printStackTrace();}}return res;}public static byte[] serializeObject(Serializable object) throws Exception {ByteArrayOutputStream baos = null;ObjectOutputStream oos = null;byte[] res = null;try {baos = new ByteArrayOutputStream();oos = new ObjectOutputStream(baos);oos.writeObject(object);oos.flush();res = baos.toByteArray();} catch (Exception ex) {throw ex;} finally {try {if(oos != null)oos.close();} catch (Exception e) {e.printStackTrace();}}return res;}public static Serializable deserializeObject(byte[] rowObject) throws Exception {ObjectInputStream ois = null;Serializable res = null;try {ois = new ObjectInputStream(new ByteArrayInputStream(rowObject));res = (Serializable) ois.readObject();} catch (Exception ex) {throw ex;} finally {try {if(ois != null)ois.close();} catch (Exception e) {e.printStackTrace();}}return res;}

下面我們展示了上述兩種方法之間的性能比較表

橫軸表示測試運行的次數,縱軸表示每次測試運行的每秒平均事務數(TPS)。 因此,較高的值更好。 如您所見,與普通的Serializable方法相比,使用Serializable方法可以在序列化和反序列化時獲得更高的性能。

最后,我們必須指出我們執行了測試,為“ Employee”對象的所有非必填字段提供了值。 如果在同一方法之間進行比較時不使用所有非強制性參數,并且最重要的是在Externalizable和Serializable方法之間進行交叉比較時,您應該期望獲得更高的性能提升。

編碼愉快!

賈斯汀

相關文章 :
  • Java最佳實踐–多線程環境中的DateFormat
  • Java最佳實踐– Vector vs ArrayList vs HashSet
  • Java最佳實踐–字符串性能和精確字符串匹配
  • Java最佳實踐–隊列之戰和鏈接的ConcurrentHashMap
  • Java最佳實踐– Char到Byte和Byte到Char的轉換

翻譯自: https://www.javacodegeeks.com/2010/07/java-best-practices-high-performance.html

java高性能序列化

總結

以上是生活随笔為你收集整理的java高性能序列化_Java最佳实践–高性能序列化的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 在线免费观看av网址 | 好吊日在线观看 | 亚洲精品短视频 | 91黑丝视频 | 18欧美性xxxx极品hd | 黄色a一片 | 亚洲图片88 | 亚洲精品字幕在线观看 | 两女双腿交缠激烈磨豆腐 | 久久精品一区二区免费播放 | 国产高清视频在线免费观看 | 人人插人人搞 | 亚洲美女操 | 无毛av| 91福利在线播放 | 在线色 | 亚洲精品喷潮一区二区三区 | 国产ts人妖调教重口男 | 女大学生的家政保姆初体验 | 亚洲天堂黄色 | 国产精品手机在线 | av片在线播放 | 一区www| 成人夜晚视频 | 在线综合av | 欧美日韩一区二区视频观看 | 亚洲AV无码AV吞精久久中文版 | 黄色av网站免费观看 | 国产精品久久久久久三级 | 一区二区内射 | 丁香九月婷婷 | 美女扒开屁股让男人桶 | 一区二区三区国产精品视频 | 国产一区二区在线免费观看 | 国产中文字幕免费 | 蜜臀尤物一区二区三区直播 | 成年人在线免费观看视频网站 | 黄色免费国产 | 国产中年熟女高潮大集合 | 高清在线一区二区 | www.69av.com| 99热91 | 精品人妻一区二区三区含羞草 | 成人亚洲精品久久久久软件 | 亚洲天堂欧美在线 | 电家庭影院午夜 | 亚洲精品久久久久久久久久 | 在线播放波多野结衣 | 国产精品久久久久久亚洲影视 | 两个人看的www视频免费完整版 | 一级黄色大片在线观看 | 伊人久久影院 | 香蕉视频啪啪 | 少妇高潮灌满白浆毛片免费看 | 国产在线极品 | 人妻熟妇又伦精品视频a | 天堂网91 | 影音先锋在线观看视频 | 91鲁| 日韩一卡二卡三卡 | 性感美女被爆操 | 久久久久99精品成人片 | 美女被草出白浆 | 日本色区 | 日韩一区二区av | 国产亚洲精品美女久久久 | 人妻一区二区三 | 先锋资源av网 | 日本中文字幕在线播放 | 国产浮力第一页 | 国产一区二区精品 | 9999精品| 又色又爽又黄gif动态图 | 成年人一级黄色片 | 欧美日韩不卡一区二区三区 | 亚洲精品国产片 | av网站在线播放 | 水蜜桃影库 | 娇妻高潮浓精白浆xxⅹ | 国产成人三级在线播放 | 国产福利免费在线观看 | 女生裸体无遮挡 | 天天躁日日躁aaaa视频 | 成人激情自拍 | www.av天天| 污污内射久久一区二区欧美日韩 | 亚洲精品国产精品乱码 | 久久久男女 | 亚洲精品国产精品国自产网站按摩 | 毛片基地视频 | 国产自产在线 | 欧美视频三区 | 五月激情久久 | 中文字幕人妻一区二区三区在线视频 | 日本精品视频一区二区 | 亚洲日日操 | 成人高潮片免费视频 | 欧美顶级黄色大片免费 | 好吊妞视频在线观看 |