001 package net.sf.cpsolver.ifs.util; 002 003 import java.io.*; 004 import java.util.*; 005 006 /** A class for reading prolog files. 007 * 008 * @version 009 * IFS 1.1 (Iterative Forward Search)<br> 010 * Copyright (C) 2006 Tomáš Müller<br> 011 * <a href="mailto:muller@unitime.org">muller@unitime.org</a><br> 012 * Lazenska 391, 76314 Zlin, Czech Republic<br> 013 * <br> 014 * This library is free software; you can redistribute it and/or 015 * modify it under the terms of the GNU Lesser General Public 016 * License as published by the Free Software Foundation; either 017 * version 2.1 of the License, or (at your option) any later version. 018 * <br><br> 019 * This library is distributed in the hope that it will be useful, 020 * but WITHOUT ANY WARRANTY; without even the implied warranty of 021 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 022 * Lesser General Public License for more details. 023 * <br><br> 024 * You should have received a copy of the GNU Lesser General Public 025 * License along with this library; if not, write to the Free Software 026 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 027 */ 028 public class PrologFile implements Iterator { 029 private java.io.BufferedReader iBufferedReader = null; 030 private Term iNextTerm = null; 031 032 public PrologFile(String file) throws java.io.IOException { 033 iBufferedReader = new BufferedReader(new FileReader(file)); 034 iNextTerm = (iBufferedReader.ready()?readTerm(new SpecialReader(iBufferedReader)):null); 035 if (iNextTerm==null) iBufferedReader.close(); else iBufferedReader.readLine(); 036 } 037 038 /** Reads a prolog file. It returns a set of terms */ 039 public static Vector readTermsFromStream(java.io.InputStream is, String term) throws java.io.IOException { 040 BufferedReader br = new BufferedReader(new InputStreamReader(is)); 041 Vector ret = new Vector(); 042 //int x=0; 043 while (br.ready()) { 044 Term t = readTerm(new SpecialReader(br)); 045 //System.out.println(t); 046 //x++; 047 //if (x>10) break; 048 if (t!=null && t.getText()!=null && t.getText().startsWith(term)) { 049 ret.addElement(t); 050 } 051 br.readLine(); 052 } 053 br.close(); 054 return ret; 055 } 056 057 /** Writes a set of terms. */ 058 public static void writeTerms(PrintWriter pw, Vector terms) throws java.io.IOException { 059 for (Enumeration e=terms.elements();e.hasMoreElements();) { 060 Term t = (Term)e.nextElement(); 061 writeTerm(pw,t); 062 } 063 } 064 065 /** reads a term */ 066 private static Term readTerm( SpecialReader is) throws IOException { 067 StringBuffer text=new StringBuffer(); 068 Vector content = null; 069 int i; 070 if ((i = is.read())>=0) { 071 while ((char)i=='%' || (char)i==':') { 072 do { 073 i=is.read(); 074 } while (i>=0 && !( i==0x0d || i==0x0a )); 075 i=is.read(); 076 if (i>=0 && (i==0x0d || i==0x0a )) i=is.read(); 077 } 078 if (i>=0) is.flush((char)i); 079 } 080 char prev = (char)i; 081 if (i>=0) while ((i = is.read())>=0) { 082 char ch = (char)i; 083 if (ch=='\n' || ch=='\r') 084 if (prev=='.') break; else continue; 085 if (ch=='(' || ch=='[') { 086 content = new Vector(); 087 content.addElement(readTerm(is)); 088 } else if (content==null && (ch==',' || ch==')' || ch==']')) { 089 is.flush(ch); 090 break; 091 } else if (ch==',') content.addElement(readTerm(is)); 092 else if (ch==')' || ch==']') break; 093 else text.append(ch); 094 prev = ch; 095 } else return null; 096 Term ret = new Term(text.toString().trim(),content); 097 return ret; 098 } 099 100 /** writes a term */ 101 private static void writeTerm( PrintWriter pw, Term t) { 102 pw.println(t.toString()+"."); 103 } 104 105 106 public boolean hasNext() { 107 return iNextTerm!=null; 108 } 109 110 public Object next() { 111 Term ret = iNextTerm; 112 try { 113 iNextTerm = (iBufferedReader.ready()?readTerm(new SpecialReader(iBufferedReader)):null); 114 } catch (java.io.IOException x) { 115 iNextTerm = null; 116 } 117 try { 118 if (iNextTerm==null) iBufferedReader.close(); else iBufferedReader.readLine(); 119 } catch (java.io.IOException x) {} 120 return ret; 121 } 122 123 public void remove() { 124 } 125 126 /** Flushable reader -- extension of java.io.Reader */ 127 private static class SpecialReader { 128 /** reader */ 129 private Reader iReader = null; 130 /** flushed characters */ 131 private StringBuffer iFlushedChars = new StringBuffer(); 132 133 /** constructor */ 134 public SpecialReader(Reader r) { 135 iReader = r; 136 } 137 138 /** reads a byte */ 139 public int read() throws java.io.IOException { 140 if (iFlushedChars.length()==0) return iReader.read(); 141 char ret=iFlushedChars.charAt(0); 142 iFlushedChars.deleteCharAt(0); 143 return ret; 144 } 145 146 /** flush (return to stream) a character */ 147 public void flush(char ch) { 148 iFlushedChars.insert(0,ch); 149 } 150 } 151 152 /** Term -- it can contain a text and a content (set of terms) */ 153 public static class Term { 154 /** text */ 155 private String iText = null; 156 /** content */ 157 private Vector iContent = null; 158 159 public boolean equals(Object o) { 160 if (o==null || !(o instanceof Term)) return false; 161 Term t = (Term)o; 162 if (iText==null && t.iText!=null) return false; 163 if (iText!=null && t.iText==null) return false; 164 if (iText!=null && !iText.equals(t.iText)) return false; 165 if (iContent==null && t.iContent!=null) return false; 166 if (iContent!=null && t.iContent==null) return false; 167 if (iContent!=null && !iContent.equals(t.iContent)) return false; 168 return true; 169 } 170 171 /** constructor */ 172 public Term(String text) { 173 iText = text; 174 iContent = null; 175 } 176 177 /** constructor */ 178 public Term(Vector content) { 179 iText = null; 180 iContent = content; 181 } 182 183 /** constructor */ 184 public Term(String text, Vector content) { 185 iText = text; 186 iContent = content; 187 } 188 189 /** constructor */ 190 public Term(String text, Term[] content) { 191 iText = text; 192 if (content==null) { 193 iContent = null; 194 } else { 195 iContent = new Vector(); 196 for (int i=0;i<content.length;i++) 197 iContent.addElement(content[i]); 198 } 199 } 200 201 /** constructor */ 202 public Term(Term[] content) { 203 this(null,content); 204 } 205 206 /** return text */ 207 public String getText() { 208 return iText; 209 } 210 211 /** return content */ 212 public Vector getContent() { 213 return iContent; 214 } 215 216 /** content size */ 217 public int size() { 218 return (iContent==null?-1:iContent.size()); 219 } 220 221 /** return text as int */ 222 public int toInt() { 223 return Integer.parseInt(iText); 224 } 225 226 /** return text as long */ 227 public long toLong() { 228 return Long.parseLong(iText); 229 } 230 231 /** return text as fouble */ 232 public double toDouble() { 233 return Double.parseDouble(iText); 234 } 235 236 /** return text as boolean */ 237 public boolean toBoolean() { 238 return (toInt()!=0); 239 } 240 241 /** return content as boolean array */ 242 public boolean[] toBooleanArray() { 243 if (iContent.size()==1 && iContent.elementAt(0).toString().length()==0) return new boolean[] {}; 244 boolean[] ret = new boolean[iContent.size()]; 245 for (int i=0;i<ret.length;i++) { 246 ret[i]=elementAt(i).toBoolean(); 247 } 248 return ret; 249 } 250 251 /** return content as string array */ 252 public String[] toStringArray() { 253 if (iContent.size()==1 && iContent.elementAt(0).toString().length()==0) return new String[] {}; 254 String[] ret = new String[iContent.size()]; 255 for (int i=0;i<ret.length;i++) { 256 Term t = elementAt(i); 257 ret[i]=(t.getText().length()>0?t.toString():t.elementAt(0).toString()); 258 } 259 return ret; 260 } 261 262 /** return content as int array */ 263 public int[] toIntArray() { 264 //System.err.println("ToIntArray: "+this); 265 if (iContent.size()==1 && iContent.elementAt(0).toString().length()==0) return new int[] {}; 266 int[] ret = new int[iContent.size()]; 267 for (int i=0;i<ret.length;i++) { 268 Term t = elementAt(i); 269 ret[i]=(t.getText().length()>0?Integer.parseInt(t.getText()):t.elementAt(0).toInt()); 270 //System.err.println(" "+i+" .. "+ret[i]); 271 } 272 return ret; 273 } 274 275 /** idx-th element of content */ 276 public Term elementAt(int idx) { 277 try { 278 return (Term)iContent.elementAt(idx); 279 } catch (Exception e) { 280 return null; 281 } 282 } 283 284 /** element of content named name*/ 285 public Term element(String name) { 286 try { 287 for (Enumeration i=iContent.elements();i.hasMoreElements();) { 288 Term t = (Term)i.nextElement(); 289 if (t.getText()!=null && t.getText().equals(name)) return t; 290 } 291 return null; 292 } catch (Exception e) { 293 return null; 294 } 295 } 296 297 /** index of element of content named name*/ 298 public int indexOf(String name) { 299 try { 300 int idx=0; 301 for (Enumeration i=iContent.elements();i.hasMoreElements();) { 302 Term t = (Term)i.nextElement(); 303 if (t.getText()!=null && t.getText().equals(name)) return idx; 304 idx++; 305 } 306 return -1; 307 } catch (Exception e) { 308 return -1; 309 } 310 } 311 312 /** string representation of term */ 313 public String toString() { 314 boolean isArray = (iText==null || iText.length()==0); 315 StringBuffer sb = new StringBuffer(isArray?"":iText); 316 if (iContent!=null) { 317 sb.append(isArray?"[":"("); 318 for (Enumeration e=iContent.elements();e.hasMoreElements();) { 319 sb.append(e.nextElement().toString()); 320 sb.append(e.hasMoreElements()?",":""); 321 } 322 sb.append(isArray?"]":")"); 323 } 324 return sb.toString(); 325 } 326 327 public Object clone() { 328 return new Term(iText==null?null:new String(iText),iContent==null?iContent:(Vector)iContent.clone()); 329 } 330 } 331 }