我搜索了几页,但大多数似乎只是对静态意味着什么的理解问题。我遇到的问题在于我们使用的是静态类,FocusListener和ActionListener。具有事件处理的类调用静态类,并且当填充JTextfield并从FocusListener选中时,立即更新该静态变量。当所有JTextfields都被填充并且FocusListener更新了变量时,就会有一个提交JButton。单击该按钮后,将调用静态方法以完成使用先前更新的变量计算的任何变量。用户不知道这一点。变量虽然没有更新,但我很好奇我是否实现了这个错误?提前谢谢。
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
public class WellParameters extends JInternalFrame implements FocusListener, ActionListener {
JLabel measuredDepthL, ..., pitGainL, drillBitSizeL,
mudInActivePitsL, mainPanelLabel;
JTextField measuredDepthT, ..., pitGainT, drillBitSizeT, mudInActivePitsT;
JPanel mainPanel, firstPanel, secondPanel, thirdPanel, fourthPanel, submitButtonPanel;
JButton submitButton;
WellParameters() {
super("Well Parameters", true, true, false, true);
this.setBounds(0, 0, 600, 385);
this.setVisible(true);
this.setLayout(new BorderLayout());
...//GUI Stuff
this.add(submitButtonPanel, BorderLayout.SOUTH);
}
@Override
public void focusGained(FocusEvent e) {} //Ignore this!
@Override
public void focusLost(FocusEvent e) {
try {
if(e.getSource() == measuredDepthT) {
KillWellCalculations.measuredDepth = Integer.parseInt(measuredDepthT.getText());
...//Others
} else if(e.getSource() == mudInActivePitsT) {
KillWellCalculations.mudInActivePits = Double.parseDouble(mudInActivePitsT.getText());
}
} catch (Exception ignore) {}
}
@Override
public void actionPerformed(ActionEvent e) {
try {
if(e.getSource() == submitButton) {
System.out.println(KillWellCalculations.pumpEfficiency);
KillWellCalculations.setPressureBeforeCasingBurstAndFormationFracture(); //Doesn't work
KillWellCalculations.setCirculatingPressures();
KillWellCalculations.setTriplexPumpCapacity();
System.out.println(KillWellCalculations.mudInActivePits);
System.out.println(KillWellCalculations.pumpFactor);
System.out.println(KillWellCalculations.finalCirculatingPressure);}
}
catch(Exception ignore) {}
}
}
那是GUI,这是静态类......它们是2个独立的类。不在同一个文件中。 包killwellsheet;
public class KillWellCalculations {
static int measuredDepth; //Total Depth from open hole to bottom
... //Tons of other variables
static double totalStrokes; //add strokes
//Used to set different circulating pressures for the well
public static void setCirculatingPressures() {
initialCirculatingPressure = circulatingPressureKillRate + shutInDrillPipePressure;
finalCirculatingPressure = circulatingPressureKillRate * (killMudWeight/currentMudWeight);
}
//Calculates capacity of anypipe
private static double pipeCapacity(double length, double insideDiameter) {
return length * ((insideDiameter*insideDiameter)/1029.4);
}
//Calculates capacity of the annulus/open hole
private static double annulusCapacity(double length, double insideDiameter, double outsideDiameter) {
return length * (((insideDiameter*insideDiameter)-(outsideDiameter*outsideDiameter))/1029.4);
}
... //Other functions
//Set the casing burst pressure
public static void setPressureBeforeCasingBurstAndFormationFracture() {
beforeCasingBurst = burstPressure*0.70;
beforeFormationFracture = (0.052*casingShoeDepth)*(fracGradientMWEquivalent - currentMudWeight);
}
public static void bariteNeedAndVolumeIncrease() {
bariteSacksRequired = (totalMudVolume/100)*((1099*(killMudWeight-currentMudWeight))/(28.35-killMudWeight));
increaseInMudVolume = 0.091*bariteSacksRequired;
}
public static void pumpStrokes() {
surfaceToBit = (mudInDrillString)/pumpFactor;
bitToSurface = (mudInAnnulus)/pumpFactor;
totalStrokes = surfaceToBit + bitToSurface;
}
}//end class
答案 0 :(得分:0)
一些澄清......通过阅读代码,我唯一看到的是你的类WellParameters实现了Interfaces FocusListener和ActionListener(不是静态类)。据我所知,从代码中可以看出,方法 focusGained(FocusEvent e)和 focusLost(FocusEvent e)是从前一个接口实现的,并更新了静态类,您将依赖于ActionListener事件 actionPerformed()中的相同计算值。您在这里遇到的问题是关于静态实例值的竞争条件。
http://java.sun.com/docs/books/performance/1st_edition/html/JPAppGC.fm.html A.3.4无法访问
对象进入无法访问状态 当没有更强烈的引用它 存在。当一个对象无法访问时, 它是收藏的候选人。注意 措辞:仅仅因为一个对象 收集候选人没有 意味着它会被立即收集。 JVM可以自由延迟收集 直到迫切需要 被消耗的内存 宾语。重要的是要注意到这一点 不仅仅是任何强有力的参考 在内存中保存一个对象。这些必须 是来自a的链接的引用 垃圾收集根。 GC的根源是 一个特殊的变量类 包括
堆栈上的临时变量(任何线程) 静态变量(来自任何类) 来自JNI本机代码的特殊引用
基于此垃圾收集文档,我怀疑您的类 KillWellCalculations 的所有静态引用都有资格在调用FocusEvent方法后进行垃圾收集,因此,在事件 actionPerformed()被触发时,它们不可用。
只有当其他类使用此类时,您仍然可以将类KillWellCalculations的静态方法用作实用程序类。如果没有,您可以将其转换为包含计算的Value类,不包含静态引用。因为你需要引用一个包含计算值的类的实例...例如:
public Class CalculatedValues {
private int measuredDepth;
private double mudInActivePits;
public static CalculatedValues makeNew() {
return new CalculatedValues();
}
public void setMeasuredDepth(String measuredDepthTString) {
if (measuredDepthTString == null) {
throw new IllegalArgumentException("The measured depth must be provided.");
}
try {
this.measuredDepth = Integer.parseInt(measuredDepthTString);
} catch(NumberFormatException nfe) {
throw new IllegalArgumentException("The value provided is not an interger.");
}
}
public int getMeasuredDepth() {
return measuredDepth;
}
public void setMudInActivePitsT(String mudInActivePitsTString) {
if (mudInActivePitsTString == null) {
throw new IllegalArgumentException("The measured mudInActivePits must be provided.");
}
try {
this.mudInActivePits = Double.parseDouble(measuredDepthTString);
} catch(NumberFormatException nfe) {
throw new IllegalArgumentException("The value provided is not an double.");
}
}
public double getMeasuredDepth() {
return mudInActivePits;
}
//...
//...
// MORE THE OTHER VALUES/PROPERTIES IMPORTANT/NEEDED BY THE CALCULATION.
public void doAllCalculations() {
// YOU HAVE TO IMPLEMENT THE LOGIC FOR THOSE ONES, OPTIONALLY USING THE SAME UTILITY/HELPER STATIC METHODS FROM
setPressureBeforeCasingBurstAndFormationFracture();
setCirculatingPressures();
setTriplexPumpCapacity();
}
}
然后,修改类的构造函数以获得值object的实例:
...
...
// THE VALUE OBJECT REFERENCE WITH THE VALUES YOU NEED TO HOLD DURING THE FORM INTERACTION
private CalculatedValues calculatedValues;
WellParameters() {
super("Well Parameters", true, true, false, true);
this.setBounds(0, 0, 600, 385);
this.setVisible(true);
this.setLayout(new BorderLayout());
...//GUI Stuff
this.add(submitButtonPanel, BorderLayout.SOUTH);
// THE VALUE OBJECT REFERENCE...
calculatedValues = CalculatedValues.makeNew();
}
然后,用计算更新参考:
@Override
public void focusLost(FocusEvent e) {
try {
if(e.getSource() == measuredDepthT) {
//KillWellCalculations.measuredDepth = Integer.parseInt(measuredDepthT.getText());
// the exceptions thrown can be caught in the catch below and you can display the error message from the value class.
calculatedValues.setMeasuredDepth(measuredDepthT.getText());
...//Others
// collect other values as well...
} else if(e.getSource() == mudInActivePitsT) {
//KillWellCalculations.mudInActivePits = Double.parseDouble(mudInActivePitsT.getText());
// do try/catch for the possible runtime exception and display an error message
calculatedValues.setMudInActivePitsT(mudInActivePitsT.getText());
}
} catch (Exception ignore) {
}
}
最后一步的更新也使用实例引用:
@Override
public void actionPerformed(ActionEvent e) {
try {
if(e.getSource() == submitButton) {
System.out.println(KillWellCalculations.pumpEfficiency);
// THE REFERENCES THAT THIS STATIC METHOD USE WERE ALL GARBAGE-COLLECTED AT THE TIME OF THE CALL... IF SHOULD HAVE THE CALCULATED METHODS IN THE VALUE CLASS. SOMETHING LIKE THE FOLLOWING:
// KillWellCalculations.setPressureBeforeCasingBurstAndFormationFracture(); //Doesn't work
//KillWellCalculations.setCirculatingPressures();
//KillWellCalculations.setTriplexPumpCapacity();
//System.out.println(KillWellCalculations.mudInActivePits);
//System.out.println(KillWellCalculations.pumpFactor);
//System.out.println(KillWellCalculations.finalCirculatingPressure);}
// DO THE FINAL CALCULATION IN A SINGLE METHOD IN THE VALUE OBJECT.
calculatedValues.doAllCalculations();
// HERE ARE THE GETTERS FROM THE CALCULATED VALUES OF THE DO ALL CALCULATIONS YOU HAVE TO IMPLEMENT.
System.out.println(calculatedValues.getMudInActivePits());
System.out.println(calculatedValues.getPumpFactor());
System.out.println(calculatedValues.getFinalCirculatingPressure());}
// CONSIDERING YOU'RE DONE WITH THE VALUES, JUST CLEAR THE INSTANCE VALUES
// AS THIS REFERENCE IS NOT STATIC AND IT WILL NOT BE GARBAGE-COLLECTED.
calculatedValues.clearValues();
}
catch(Exception ignore) {}
}
我做了一些与GUI相关的工作......您可以在http://code.google.com/p/marcellodesales-cs-research/source/browse/trunk/grad-ste-ufpe-brazil/ptf-add-on-dev/src/br/ufpe/cin/stp/ptfaddon/view/swing/execution/JWizardInternalFrame.java看到一个非常相似的例子
祝你好运!