📄 spellchecker.java
字号:
import java.awt.BorderLayout;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.Vector;
import javax.swing.*;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
public class spellChecker extends JFrame
implements KeyListener, ActionListener, ListSelectionListener
{
private JTextField jtf=new JTextField();
private static JList list=new JList();
private static JTextArea jta=new JTextArea();
private JButton button =new JButton(" 查询 ");
private JScrollPane scrollPane1=new JScrollPane(list);
private static Vector wordVector=new Vector(); //存放英语单词的向量
private static int[] searchIndex=new int[27]; //一级索引
private static Vector matchWordIndex=new Vector(); //存放找到的参考单词所在向量中的位置
public spellChecker()
{
Container container =getContentPane();
container.setLayout(new BorderLayout());
JPanel jp1=new JPanel();
jp1.setLayout(new BorderLayout());
jp1.add(new JLabel(" 输入 "),BorderLayout.WEST);
jp1.add(jtf,BorderLayout.CENTER);
jp1.add(button,BorderLayout.EAST);
container.add(jp1,BorderLayout.NORTH);
container.add(scrollPane1,BorderLayout.WEST);
JScrollPane scrollPanel2=new JScrollPane(jta);
jta.setEditable(false);
container.add(scrollPanel2,BorderLayout.CENTER );
list.addListSelectionListener(this);
button.addActionListener(this);
jtf.addKeyListener(this);
}
public static void main(String[] args)
{
try
{
addDictionary();
} catch (IOException e)
{
e.printStackTrace();
}
spellChecker checkerFrame=new spellChecker();
checkerFrame.pack();
checkerFrame.setTitle("SPELL CHECKER");
checkerFrame.setSize(600,500);
Dimension screenSize=Toolkit.getDefaultToolkit().getScreenSize();
int screenWidth = screenSize.width;
int screenHeight = screenSize.height;
Dimension frameSize=checkerFrame.getSize();
int x=(screenWidth-frameSize.width)/2;
int y=(screenHeight-frameSize.height)/2;
checkerFrame.setLocation(x,y);
checkerFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
checkerFrame.setVisible(true);
}
public void keyPressed(KeyEvent e)
{
// TODO Auto-generated method stub
}
public void keyReleased(KeyEvent e)
{
// TODO Auto-generated method stub
int key=e.getKeyCode();
//System.out.println("KeyTyped :"+ key);
if(key==KeyEvent.VK_ENTER) //输入完后按回车查询单词
{
String str=jtf.getText().trim();
if(str.length()>0)
{
int index=search(str);
jta.setText("");
if(index==-1)
{
jta.append("单词拼写错误\n");
matchWordIndex.removeAllElements();
giveWords(str); //查找可能的与输入相近的单词
if(matchWordIndex.size()>0)
{
jta.append("拼写校正 你要输入的单词是不是:\n");
for (int i=0;i<matchWordIndex.size();i++)
{
Integer integerObject=(Integer)(matchWordIndex.elementAt(i));
int matchIndex=integerObject.intValue();
jta.append(wordVector.elementAt(matchIndex)+" "+getExplanation(matchIndex)+"\n");
}
}
else
jta.append("找不到与你输入相近的单词\n");
}
else
{
String explanation=new String(getExplanation(index));
jta.append(explanation+"\n");
}
//jtf.setText("");
}
}
if(key==KeyEvent.VK_DELETE) //按DELETE键
{
String str=jtf.getText().trim();
if(str.length()>0)
{
int index=perSearch(str);
System.out.println(index);
list.setSelectedIndex(index);
scrollPane1.getVerticalScrollBar().setValue(index*20);
}
}
else if(key==KeyEvent.VK_DOWN) //按down键
{
int index=list.getSelectedIndex();
index++;
list.setSelectedIndex(index);
scrollPane1.getVerticalScrollBar().setValue(index*20);
jtf.setText((String) wordVector.elementAt(index));
}
else if(key==KeyEvent.VK_UP) //按up键
{
int index=list.getSelectedIndex();
index--;
list.setSelectedIndex(index);
scrollPane1.getVerticalScrollBar().setValue(index*20);
jtf.setText((String) wordVector.elementAt(index));
}
else
{
String str=jtf.getText().trim();
if(str.length()>0)
{
int index=perSearch(str);
System.out.println(index);
list.setSelectedIndex(index);
scrollPane1.getVerticalScrollBar().setValue(index*20);
}
}
}
public void keyTyped(KeyEvent e)
{
// TODO Auto-generated method stub
}
public void actionPerformed(ActionEvent e)
{
// TODO Auto-generated method stub
if(e.getSource()==button) //输入完后按查询按钮查询单词
{
String str=jtf.getText().trim();
if(str.length()>0)
{
int index=search(str);
jta.setText("");
if(index==-1)
{
jta.append("单词拼写错误\n");
giveWords(str);
if(matchWordIndex.size()>0)
{
jta.append("拼写校正 你要输入的单词是不是:\n");
for (int i=0;i<matchWordIndex.size();i++)
{
Integer integerObject=(Integer)(matchWordIndex.elementAt(i));
int matchIndex=integerObject.intValue();
jta.append(wordVector.elementAt(matchIndex)+" "+getExplanation(matchIndex)+"\n");
}
}
else
jta.append("找不到与你输入相近的单词\n");
}
else
{
String explanation=new String(getExplanation(index));
jta.append(explanation+"\n");
}
//jtf.setText("");
}
}
}
public void valueChanged(ListSelectionEvent arg0)
{
// TODO Auto-generated method stub
int index=list.getSelectedIndex();
System.out.println(index);
//jtf.setText((String) wordVector.elementAt(index));
String explanation=new String(getExplanation(index));
jta.setText("");
jta.append(explanation+"\n");
}
public static void addDictionary() throws IOException
{
// TODO 将英文字典读入,同时建立一级索引
BufferedReader wordFile=null;
String inLine;
try
{
wordFile=new BufferedReader(new FileReader("wordList.txt"));
searchIndex[0]=0; //a的起始位置
int index=1;
while((inLine=wordFile.readLine())!=null)
{
wordVector.add(inLine); //将读入的单词存放在向量中
char ch=inLine.charAt(0);
if(ch<'Z'&&ch >'A') //如果首字母是大写,将其转换为小写,便于处理
ch=(char)((int)ch-'A'+'a');
if((int)ch-97-index==0) //同时建立一级索引
{
searchIndex[index]=wordVector.size()-1;
index++;
}
}
list=new JList(wordVector);
searchIndex[26]=wordVector.size()-1;
}
catch(FileNotFoundException ex)
{
System.out.println("File not found :");
}
finally
{
try
{
if(wordFile!=null)
wordFile.close();
}
catch (IOException ex)
{
System.out.println(ex.getMessage());
}
}
}
public static String getExplanation(int index)
{
//TODO 显示英文单词所对应的中文解释
BufferedReader explanationFile = null;
String explanation="";
try
{
explanationFile=new BufferedReader(new FileReader("explanationList.txt"));
for(int i=0;i<=index;i++)
explanation=explanationFile.readLine();
}
catch(IOException ex)
{
System.out.println("Error:"+ex);
}
finally
{
try
{
if(explanationFile!=null)
explanationFile.close();
}
catch (IOException ex)
{
System.out.println(ex.getMessage());
}
}
int i=0;
while(explanation.charAt(i)!='$')
i++;
explanation=explanation.substring(i+1);
return explanation;
}
public int search (String str)
{
//TODO 查找,采用一级索引加二分查找法,若找到,返回该单词所在向量的位置;找不到,返回-1
char ch=str.charAt(0);
if(ch<'Z'&&ch >'A')
ch=(char)((int)ch-'A'+'a');
int head=searchIndex[(int)ch-97];
int tail=searchIndex[(int)ch-96];
return binarySearch(str, wordVector, head, tail-1);
}
public int binarySearch(String str,Vector vector,int head ,int tail)
{
//TODO 递归二分查找法
if((tail-head)==1)
{
if(((String)wordVector.elementAt(head)).equals(str))
return head;
else if(((String)wordVector.elementAt(tail)).equals(str))
return tail;
else
return -1;
}
else
{
int mid=(head+tail)/2;
int result=((String)wordVector.elementAt(mid)).compareToIgnoreCase(str);
if(result<0)
return binarySearch(str,wordVector,mid,tail);
else if(result>0)
return binarySearch(str,wordVector,head,mid);
else
return mid;
}
}
public int perSearch(String str)
{
//TODO 联想搜索
char ch=str.charAt(0);
if(ch<'Z'&&ch >'A')
ch=(char)((int)ch-'A'+'a');
int head=searchIndex[(int)ch-97];
int tail=searchIndex[(int)ch-96];
return binaryPerSearch(str, wordVector, head, tail-1);
}
public int binaryPerSearch(String str,Vector vector,int head ,int tail)
{
//TODO 联想二分查找
if((tail-head)==1)
{
if(((String)wordVector.elementAt(head)).equals(str))
return head;
else if(((String)wordVector.elementAt(tail)).equals(str))
return tail;
else
{
int result=((String)wordVector.elementAt(head)).compareToIgnoreCase(str);
if(result<0)
return tail;
else
return head;
}
}
else
{
int mid=(head+tail)/2;
int result=((String)wordVector.elementAt(mid)).compareToIgnoreCase(str);
if(result<0)
return binaryPerSearch(str,wordVector,mid,tail);
else if(result>0)
return binaryPerSearch(str,wordVector,head,mid);
else
return mid;
}
}
public void giveWords(String str)
{
//TODO 给出参考的单词序列
insertLetter(str);
deleteLetter(str);
changeLetter(str);
swapLetter(str);
}
public void insertLetter(String str)
{
//TODO 在给定的字符串中插入一个字母,看能不能找到正确的单词
char[] tempStr=str.toCharArray();
for (int i=1;i<str.length()+1;i++)
{
for (int ch=(int)'a';ch<=(int)'z';ch++)
{
String newStr=new String (insertChar(tempStr,i,(char)ch)); //在字符串的第i个位置插入字母ch
int index=search(newStr);
if(index!=-1)
if(matchWordIndex.indexOf(new Integer(index))==-1)
matchWordIndex.addElement(new Integer(index));
}
}
}
public void deleteLetter(String str)
{
//TODO 删除给定的字符串中的一个字母,看能不能找到正确的单词
char[] tempStr=str.toCharArray();
for (int i=1;i<str.length();i++)
{
String newStr=new String (deleteChar(tempStr,i)); //删除第i个字母
int index=search(newStr);
if(index!=-1)
if(matchWordIndex.indexOf(new Integer(index))==-1)
matchWordIndex.addElement(new Integer(index));
}
}
public void changeLetter(String str)
{
//TODO 替换给定字符串中的一个字母,看能不能找到正确的单词
char[] tempStr=str.toCharArray();
for (int i=1;i<str.length();i++)
{
for (int ch=(int)'a';ch<=(int)'z';ch++)
{
String newStr=new String (changeChar(tempStr,i,(char)ch)); //将字符串的第i个位置替换为字母ch
int index=search(newStr);
if(index!=-1)
if(matchWordIndex.indexOf(new Integer(index))==-1)
matchWordIndex.addElement(new Integer(index));
}
}
}
public void swapLetter(String str)
{
//TODO 交换单词中的字母,看能不能找到正确的单词
char[] tempStr=str.toCharArray();
for (int i=1;i<str.length()-1;i++) //交换相邻的两个字母
{
String newStr=new String (swapNeighbour(tempStr,i)); //交换字符串的第i个位置与第i+1个位置的字母
int index=search(newStr);
if(index!=-1)
if(matchWordIndex.indexOf(new Integer(index))==-1)
matchWordIndex.addElement(new Integer(index));
}
for(int i=0;i<str.length()-2;i++) //交换相隔的两个字母
{
String newStr=new String (swapApart(tempStr,i)); //交换字符串的第i个位置与第i+2个位置的字母
int index=search(newStr);
if(index!=-1)
if(matchWordIndex.indexOf(new Integer(index))==-1)
matchWordIndex.addElement(new Integer(index));
}
}
public char[] insertChar(char[] charStr,int location,char ch)
{
//TODO 将给定字符插入给定字符串的给定位置
char[] temp=new char[charStr.length+1];
for(int i=0;i<charStr.length+1;i++)
{
if(i<location)
temp[i]=charStr[i];
else if(i==location)
temp[i]=ch;
else
temp[i]=charStr[i-1];
}
return temp;
}
public char[] deleteChar(char[] charStr,int location)
{
//TODO 将给定位置的字符删除
char[] temp=new char[charStr.length-1];
for(int i=0;i<charStr.length-1;i++)
{
if(i<location)
temp[i]=charStr[i];
else
temp[i]=charStr[i+1];
}
return temp;
}
public char[] changeChar(char[] charStr,int location,char ch)
{
//TODO 将给定位置的字符替换为给定字符
char[] temp=new char[charStr.length];
for(int i=0;i<charStr.length;i++)
{
if(i==location)
temp[i]=ch;
else
temp[i]=charStr[i];
}
return temp;
}
public char[] swapNeighbour(char[]charStr,int location)
{
//TODO 将给定位置的字母与其后一个字母互换
char[] temp=new char[charStr.length];
for(int i=0;i<charStr.length;i++)
{
if(i==location)
temp[i]=charStr[i+1];
else if(i==location+1)
temp[i]=charStr[i-1];
else
temp[i]=charStr[i];
}
return temp;
}
public char[] swapApart(char[]charStr,int location)
{
//TODO 将给定位置的字母与其后第二个字母互换
char[] temp=new char[charStr.length];
for(int i=0;i<charStr.length;i++)
{
if(i==location)
temp[i]=charStr[i+2];
else if(i==location+2)
temp[i]=charStr[i-2];
else
temp[i]=charStr[i];
}
return temp;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -