📄 attributevisualizationpanel.java
字号:
maxValue = as.nominalCounts[i];
}
for(int k=0; k<m_data.numInstances(); k++) {
if(!m_data.instance(k).isMissing(attribIndex))
{
histCounts[(int)m_data.instance(k).value(attribIndex)]++;
}
}
threadRun=false;
histBarCounts = histCounts;
//Image tmpImg = new BufferedImage(getWidth(), getHeight(), BufferedImage.TYPE_INT_RGB);
//drawGraph( tmpImg.getGraphics() );
//img = tmpImg;
AttributeVisualizationPanel.this.repaint();
}
}
}
}
private class HistCalc extends Thread {
/****Code for M.P.Wand's method of histogram bin width selection.
* There is some problem with it. It always comes up -ve value
* which is raised to the power 1/3 and gives an NAN.
private static final int M=400;
private double psi(int r, double g) {
double val;
double sum=0.0;
for(int i=0; i<M; i++) {
double valCjKj=0.0;
for(int j=0; j<M; j++) {
valCjKj += c(j) * k(r, j-i, g);
}
sum += valCjKj*c(i);
}
val = Math.pow(m_data.numInstances(), -2) * sum;
//System.out.println("psi returns: "+val);
return val;
}
private double g21() {
double val;
val = Math.pow(2 / ( Math.sqrt(2D*Math.PI)*psi(4, g22())*m_data.numInstances() ), 1/5D) * Math.sqrt(2) * as.numericStats.stdDev;
//System.out.println("g21 returns: "+val);
return val;
}
private double g22() {
double val;
val = Math.pow( 2D/(5*m_data.numInstances()), 1/7D) * Math.sqrt(2) * as.numericStats.stdDev;
//System.out.println("g22 returns: "+val);
return val;
}
private double c(int j) {
double val=0.0;
double sigma = (as.numericStats.max - as.numericStats.min)/(M-1);
//System.out.println("In c before doing the sum we have");
//System.out.println("max: " +as.numericStats.max+" min: "+as.numericStats.min+
// " sigma: "+sigma);
for(int i=0; i<m_data.numInstances(); i++) {
if(!m_data.instance(i).isMissing(attribIndex))
val += Math.max( 0,
( 1 - Math.abs( Math.pow(sigma, -1)*(m_data.instance(i).value(attribIndex) - j) ) )
);
}
//System.out.println("c returns: "+val);
return val;
}
private double k(int r, int j, double g) {
double val;
double sigma = (as.numericStats.max - as.numericStats.min)/(M-1);
//System.out.println("Before calling L we have");
//System.out.println("Max: "+as.numericStats.max+" Min: "+as.numericStats.min+"\n"+
// "r: "+r+" j: "+j+" g: "+g);
val = Math.pow( g, -r-1) * L(sigma*j/g);
//System.out.println("k returns: "+val);
return val;
}
private double L(double x) {
double val;
val = Math.pow( 2*Math.PI, -1/2D ) * Math.exp( -(x*x)/2D );
//System.out.println("L returns: "+val);
return val;
}
*******End of Wand's method
*/
public void run() {
synchronized (m_locker) {
if((classIndex >= 0) && (m_data.attribute(classIndex).isNominal())) {
int intervals; double intervalWidth=0.0;
//This uses the M.P.Wand's method to calculate the histogram's interval width.
//See "Data-Based Choice of Histogram Bin Width".
//intervalWidth = Math.pow( 6D/( -psi(2, g21()) * m_data.numInstances() ), 1/3D );
//This uses the Scott's method to calculate the histogram's interval width.
//See "On optimal and data-based histograms". Biometrika, 66, 605-610 or
//see the same paper mentioned above.
intervalWidth = 3.49 * as.numericStats.stdDev * Math.pow(m_data.numInstances(), -1/3D);
//The Math.max is introduced to remove the possibility of intervals=0 that can happen
//if the intervalWidth<1
intervals = Math.max(1, (int)Math.round((as.numericStats.max - as.numericStats.min)/intervalWidth));
//System.out.println("Max: "+as.numericStats.max+" Min: "+as.numericStats.min+" stdDev: "+as.numericStats.stdDev+
// "intervalWidth: "+intervalWidth);
if(intervals > AttributeVisualizationPanel.this.getWidth()) {
intervals = AttributeVisualizationPanel.this.getWidth()-4;
if(intervals<1)
intervals = 1;
}
int histClassCounts[][] = new int[intervals][m_data.attribute(classIndex).numValues()+1];
double barRange = (as.numericStats.max - as.numericStats.min)/(double)histClassCounts.length;
double currentBar = as.numericStats.min; // + barRange;
maxValue = 0;
if(m_colorList.size()==0)
m_colorList.addElement(Color.black);
for(int i=m_colorList.size(); i<m_data.attribute(classIndex).numValues()+1; i++) {
Color pc = m_defaultColors[(i-1) % 10];
int ija = (i-1) / 10;
ija *= 2;
for (int j=0;j<ija;j++) {
pc = pc.darker();
}
m_colorList.addElement(pc);
}
for(int k=0; k<m_data.numInstances(); k++)
{
int t=0;
try {
if(!m_data.instance(k).isMissing(attribIndex)) {
t = (int) Math.ceil((float)((m_data.instance(k).value(attribIndex)-as.numericStats.min)/barRange));
if(t==0)
{
if(m_data.instance(k).isMissing(classIndex))
histClassCounts[t][0]++;
else
histClassCounts[t][(int)m_data.instance(k).value(classIndex)+1]++;
//if(histCounts[t]>maxValue)
// maxValue = histCounts[t];
} else
{
if(m_data.instance(k).isMissing(classIndex))
histClassCounts[t-1][0]++;
else
histClassCounts[t-1][(int)m_data.instance(k).value(classIndex)+1]++;
//if(histCounts[t-1]>maxValue)
// maxValue = histCounts[t-1];
}
}
}
catch(ArrayIndexOutOfBoundsException ae) {
System.out.println("t:"+(t)+
" barRange:"+barRange+
" histLength:"+histClassCounts.length+
" value:"+m_data.instance(k).value(attribIndex)+
" min:"+as.numericStats.min+
" sumResult:"+(m_data.instance(k).value(attribIndex)-as.numericStats.min)+
" divideResult:"+(float)((m_data.instance(k).value(attribIndex)-as.numericStats.min)/barRange)+
" finalResult:"+
Math.ceil((float)((m_data.instance(k).value(attribIndex)-as.numericStats.min)/barRange)) ); }
}
for(int i=0; i<histClassCounts.length; i++) {
int sum=0;
for(int j=0; j<histClassCounts[i].length; j++)
sum = sum+histClassCounts[i][j];
if(maxValue<sum)
maxValue = sum;
}
histBarClassCounts = histClassCounts;
m_barRange = barRange;
}
else { //else if the class attribute is numeric or the class is not set
int intervals = as.totalCount>10 ?
(int)(as.totalCount*0.1):(int)as.totalCount;//At the time of this coding the
//possibility of datasets with zero instances
//was being dealt with in the
//PreProcessPanel of weka Explorer.
if(intervals > AttributeVisualizationPanel.this.getWidth()) {
intervals = AttributeVisualizationPanel.this.getWidth()-4;
if(intervals<1)
intervals = 1;
}
int histCounts[] = new int[intervals];
double barRange = (as.numericStats.max - as.numericStats.min)/(double)histCounts.length;
double currentBar = as.numericStats.min; // + barRange;
maxValue = 0;
for(int k=0; k<m_data.numInstances(); k++) {
int t=0;
try {
/* if (Double.isNaN(m_data.instance(k).value(attribIndex)))
{
// Skip NaN
continue;
}*/
if(!m_data.instance(k).isMissing(attribIndex))
{
t = (int) Math.ceil((float)((m_data.instance(k).value(attribIndex)-as.numericStats.min)/barRange));
if(t==0)
{
histCounts[t]++;
if(histCounts[t]>maxValue)
maxValue = histCounts[t];
} else {
histCounts[t-1]++;
if(histCounts[t-1]>maxValue)
maxValue = histCounts[t-1];
}
}
} catch(ArrayIndexOutOfBoundsException ae) {
ae.printStackTrace();
System.out.println("t:"+(t)+
" barRange:"+barRange+
" histLength:"+histCounts.length+
" value:"+m_data.instance(k).value(attribIndex)+
" min:"+as.numericStats.min+
" sumResult:"+(m_data.instance(k).value(attribIndex)-as.numericStats.min)+
" divideResult:"+(float)((m_data.instance(k).value(attribIndex)-as.numericStats.min)/barRange)+
" finalResult:"+
Math.ceil((float)((m_data.instance(k).value(attribIndex)-as.numericStats.min)/barRange)) ); }
}
histBarCounts = histCounts;
m_barRange = barRange;
}
threadRun=false;
//Image tmpImg = new BufferedImage(getWidth(), getHeight(), BufferedImage.TYPE_INT_RGB);
//drawGraph( tmpImg.getGraphics() );
//img = tmpImg;
AttributeVisualizationPanel.this.repaint();
}
}
}
/**
* Returns "<nominal value> [<nominal value count>]"
* if displaying a bar plot and mouse is on some bar.
* If displaying histogram then it
* <li>returns "count <br> [<bars Range>]" if mouse is
* on the first bar. </li>
* <li>returns "count <br> (<bar's Range>]" if mouse is
* on some bar other than the first one. </li>
* Otherwise it returns ""
*
* @param ev The mouse event
*/
public String getToolTipText(MouseEvent ev) {
if(as!=null && as.nominalCounts!=null) {
float intervalWidth = this.getWidth()/(float)as.nominalCounts.length, heightRatio;
int barWidth, x=0, y=0;
if(intervalWidth>5)
barWidth = (int)Math.floor(intervalWidth*0.8F);
else
barWidth = 1;
x = x + (int)( (Math.floor(intervalWidth*0.1F))<1 ? 1:(Math.floor(intervalWidth*0.1F)) );
if( this.getWidth() -
(x + as.nominalCounts.length*barWidth
+(int)( (Math.floor(intervalWidth*0.2F))<1 ? 1:(Math.floor(intervalWidth*0.2F)) )*as.nominalCounts.length) > 5 )
x += (this.getWidth() -
(x + as.nominalCounts.length*barWidth +
(int)( (Math.floor(intervalWidth*0.2F))<1 ? 1:(Math.floor(intervalWidth*0.2F)) )*as.nominalCounts.length))/2;
for(int i=0; i<as.nominalCounts.length; i++) {
heightRatio = (this.getHeight()-(float)fm.getHeight())/maxValue;
y = this.getHeight()-Math.round(as.nominalCounts[i]*heightRatio);
if(ev.getX()>=x && ev.getX()<=x+barWidth
&& ev.getY()>=this.getHeight()-Math.round(as.nominalCounts[i]*heightRatio) )
return(m_data.attribute(attribIndex).value(i)+" ["+as.nominalCounts[i]+"]");
x = x+barWidth+(int)( (Math.floor(intervalWidth*0.2F))<1 ? 1:(Math.floor(intervalWidth*0.2F)) );
}
}
else if(threadRun==false && (histBarCounts!=null || histBarClassCounts!=null)) {
float heightRatio, intervalWidth;
int x=0, y=0, barWidth;
double bar = as.numericStats.min;
if((classIndex >= 0) && (m_data.attribute(classIndex).isNominal())) {
barWidth = ((this.getWidth()-6)/histBarClassCounts.length)<1 ? 1:((this.getWidth()-6)/histBarClassCounts.length);
x = 3;
if( (this.getWidth() - (x + histBarClassCounts.length*barWidth)) > 5 )
x += (this.getWidth() - (x + histBarClassCounts.length*barWidth))/2;
heightRatio = (this.getHeight()-(float)fm.getHeight())/maxValue;
if( ev.getX()-x >= 0) {
int temp = (int)((ev.getX()-x)/(barWidth+0.0000000001));
if(temp == 0){
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -