hashmap线程不安全的代码例子
时间: 2023-10-19 16:18:56 浏览: 39
当多个线程同时访问HashMap时,可能会导致数据不一致的情况,例如:
```java
Map<String, Integer> map = new HashMap<>();
// 线程1添加数据
new Thread(() -> {
for (int i = 0; i < 100000; i++) {
map.put("key" + i, i);
}
}).start();
// 线程2读取数据
new Thread(() -> {
for (int i = 0; i < 100000; i++) {
if (map.containsKey("key" + i)) {
Integer value = map.get("key" + i);
System.out.println(value);
}
}
}).start();
```
在上面的代码中,当线程1执行put操作时,可能会与线程2同时执行get操作,导致读取到的数据不一致。可以使用ConcurrentHashMap来保证线程安全。
相关问题
hashmap代码例子
下面是一个简单的 Java 实现的 HashMap 代码例子:
```java
import java.util.HashMap;
public class MyHashMap {
public static void main(String[] args) {
// 创建一个 HashMap 对象
HashMap<String, Integer> hashMap = new HashMap<>();
// 添加键值对
hashMap.put("apple", 1);
hashMap.put("banana", 2);
hashMap.put("orange", 3);
// 获取值
System.out.println(hashMap.get("apple"));
System.out.println(hashMap.get("banana"));
System.out.println(hashMap.get("orange"));
// 删除键值对
hashMap.remove("banana");
// 遍历 HashMap
for (String key : hashMap.keySet()) {
System.out.println(key + ": " + hashMap.get(key));
}
}
}
```
输出结果:
```
1
2
3
apple: 1
orange: 3
```
注意,HashMap 是一个非线程安全的类,如果在多线程环境下使用,需要进行同步处理。
写一段java线程监控sybase表变更的代码,并将变更字段结果和初始数据用json输出,注意表没有唯一键
由于表没有唯一键,我们无法通过类似于JDBC ResultSet的方式来实现监控Sybase表变更的功能。但是,我们可以通过轮询数据库表,比较前后两次轮询的结果,来判断是否有数据变更。
以下是一个简单的例子,实现了监控Sybase表变更的功能:
```java
import java.sql.*;
import java.util.*;
import com.alibaba.fastjson.*;
public class SybaseTableMonitor implements Runnable {
private final String url;
private final String username;
private final String password;
private final String tableName;
private final List<String> columns;
private final long pollInterval;
private Map<String, Object> lastRow;
public SybaseTableMonitor(String url, String username, String password,
String tableName, List<String> columns, long pollInterval) {
this.url = url;
this.username = username;
this.password = password;
this.tableName = tableName;
this.columns = columns;
this.pollInterval = pollInterval;
this.lastRow = null;
}
public void run() {
try {
Class.forName("com.sybase.jdbc4.jdbc.SybDriver");
while (true) {
Map<String, Object> currentRow = queryLastRow();
if (lastRow != null && !currentRow.equals(lastRow)) {
System.out.println("Table " + tableName + " changed:");
System.out.println("Before: " + JSON.toJSONString(lastRow));
System.out.println("After: " + JSON.toJSONString(currentRow));
}
lastRow = currentRow;
Thread.sleep(pollInterval);
}
} catch (Exception e) {
e.printStackTrace();
}
}
private Map<String, Object> queryLastRow() throws Exception {
Connection conn = DriverManager.getConnection(url, username, password);
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT TOP 1 " + String.join(",", columns) + " FROM " + tableName + " ORDER BY rowid DESC");
Map<String, Object> row = new HashMap<>();
if (rs.next()) {
for (String column : columns) {
Object value = rs.getObject(column);
row.put(column, value);
}
}
rs.close();
stmt.close();
conn.close();
return row;
}
public static void main(String[] args) {
String url = "jdbc:sybase:Tds:localhost:5000/sybase";
String username = "sa";
String password = "password";
String tableName = "my_table";
List<String> columns = Arrays.asList("column1", "column2", "column3");
long pollInterval = 1000;
SybaseTableMonitor monitor = new SybaseTableMonitor(url, username, password, tableName, columns, pollInterval);
Thread thread = new Thread(monitor);
thread.start();
}
}
```
在这个例子中,我们使用了Sybase的JDBC驱动来连接数据库。在run()方法中,我们不断地轮询数据库表,比较前后两次轮询的结果是否相同。如果有变更,则输出变更前后的JSON数据。
注意,由于表没有唯一键,我们选择了按照rowid排序来查询最新的一行数据。这种方式虽然有一定的局限性,但在很多情况下是可行的。如果您有更好的解决方案,请在评论区留言,谢谢!