public class Test {
private static SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
private static class Task implements Runnable {
public void run() {
try {
System.out.println(sdf.parse("2016-03-21 12:00:00").getTime());
} catch (ParseException e) {
e.printStackTrace();
}
}
}
public static void main(String[] args) {
Task task = new Task();
Thread t1 = new Thread(task);
t1.start();
Thread t2 = new Thread(task);
t2.start();
Thread t3 = new Thread(task);
t3.start();
Thread t4 = new Thread(task);
t4.start();
Thread t5 = new Thread(task);
t5.start();
}
}
最近才知道,如果像上面代码那样通过定义静态共享的实例来使用SimpleDateFormat是会存在线程安全问题的。
例如线程被挂死:
或者转换的时间不对:
然后自己尝试读JDK源码来试图分析在SimpleDateFormat的代码中,究竟是哪里的函数或者代码会引起线程不安全,但是由于水平有限,最后还是找不出。
哪位大牛可以帮忙分析一下。
PS:我的jdk版本:1.8.0_73
J'ai jeté un œil aux commentaires du code source de parse(), et il y a une section écrite par cette personne
calendrier} pour produire une {@code Date} Tous les {@code
calendar} sont {@linkplain Calendar#clear()
effacé} avant l'analyse, et la valeur par défaut du {@code calendrier}
les valeurs des champs date-heure sont utilisées pour tout élément manquant
informations date-heure.
La signification générale est que la méthode parse() utilise le calendrier pour générer l'instance Date renvoyée. Le problème est que le calendrier qu'elle utilise ici n'est pas nouveau à chaque fois que la méthode est exécutée. Elle définit un "Calendrier protégé". "calendrier", selon la signification du commentaire, avant chaque analyse, tous les attributs pertinents du calendrier seront effacés, puis l'objet sera rempli avec de nouveaux résultats de traitement. Dans ce cas, en multi-threads, lors de l'exécution de parse(), ce sera le cas. Après qu'un thread vient de définir le calendrier, un autre thread l'efface. Comme il s'agit d'une instance sdf, d'autres problèmes devraient être causés par cela
.Le calendrier utilisé ici est un membre de classe, et setTime multithread entraînera des problèmes de sécurité des threads
Cela n'a rien à voir avec l'implémentation de SimpleDateFormat. Cela a à voir avec le fait que vous utilisez le même objet dans plusieurs threads et que vous ne parvenez pas à synchroniser les threads