Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cassandra/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在Java中,创建一个通用的解析字符串缓存(多个结果类型)_Java - Fatal编程技术网

在Java中,创建一个通用的解析字符串缓存(多个结果类型)

在Java中,创建一个通用的解析字符串缓存(多个结果类型),java,Java,我试图创建一个通用的解析字符串缓存,以防止反复重建同一个对象。基本上,我正在构建的是以下内容: public class ParsedStringCache { // static Map<Pair<String, Parser<T>>, T> _cache // = new HashMap<Pair<String, Parser<T>>, T>(); public interface

我试图创建一个通用的解析字符串缓存,以防止反复重建同一个对象。基本上,我正在构建的是以下内容:

public class ParsedStringCache {

    // static Map<Pair<String, Parser<T>>, T> _cache
    //      = new HashMap<Pair<String, Parser<T>>, T>();

    public interface StringParser<T> {
        public T parseString(String stringToParse);
    }

    public static <T> T getParsedObject(String stringToParse, Parser<T> parser) {
        return parser.parseString(stringToParse);
    }
}
公共类ParsedStringCache{
//静态映射缓存
//=新HashMap();
公共接口字符串分析器{
公共T parseString(String stringToParse);
}
公共静态T getParsedObject(字符串stringToParse,解析器){
返回parser.parseString(stringToParse);
}
}

在我尝试实际缓存结果之前,这一切都很好,例如,通过使用类似于上面代码中注释掉的hashmap的东西,这将本质上记住getParsedObject的结果。有没有一种相当简单的方法可以避免强制转换呢?

我会让缓存成为解析器的一部分。我肯定您会遇到某种编译错误,需要解决,但下面是我将要做的基本操作

import java.util.*;
abstract class Parser<T> {

    private Map<String,T> cache = new HashMap<String,T>();

    public final T parseString(String str) {
        T result = cache.get(str);
        if(result == null) {
            result = parseString0(str);
            cache.put(str,result);
        }
        return result;
    }

    protected abstract T parseString0(String str);

}

public class IntParser extends Parser<Integer> {

    protected Integer parseString0(String str) {
        return Integer.parseInt(str.trim());
    }

}

public class LongParser extends Parser<Long> {

    protected Long parseString0(String str) {
        return Long.parseLong(str.trim());
    }

}

class ParserTest {
    public static void main(String[] args) {
        Parser<Integer> intParse = new IntParser();
        Parser<Long> longParse = new LongParser();

        Long long1 = longParse.parseString("10000");
        Long long2 = longParse.parseString("20000");
        Long long3 = longParse.parseString("30000");
        Long equalLong = longParse.parseString("20000"); // repeat long2
        Long fakeLong = new LongParser().parseString("20000"); // repeated with fake
        System.out.println("Expecting true: " + (long2 == equalLong));
        System.out.println("Expecting false: " + (fakeLong == equalLong));
    }
}

C:\Documents and Settings\glowcoder\My Documents>javac Parser.java

C:\Documents and Settings\glowcoder\My Documents>javac IntParser.java

C:\Documents and Settings\glowcoder\My Documents>javac LongParser.java

C:\Documents and Settings\glowcoder\My Documents>javac ParserTest.java

C:\Documents and Settings\glowcoder\My Documents>java ParserTest
Expecting true: true
Expecting false: false
import java.util.*;
抽象类解析器{
私有映射缓存=新的HashMap();
公共最终解析字符串(字符串str){
T result=cache.get(str);
如果(结果==null){
结果=0(str);
cache.put(str,result);
}
返回结果;
}
受保护的抽象T parseString0(String str);
}
公共类IntParser扩展了语法分析器{
受保护的整数parseString0(字符串str){
返回Integer.parseInt(str.trim());
}
}
公共类长语法分析器扩展语法分析器{
受保护的长parseString0(字符串str){
返回Long.parseLong(str.trim());
}
}
类ParserTest{
公共静态void main(字符串[]args){
Parser intParse=新的IntParser();
Parser longParse=新的LongParser();
Long long1=longParse.parseString(“10000”);
Long long2=longParse.parseString(“20000”);
Long long3=longParse.parseString(“30000”);
Long equalLong=longParse.parseString(“20000”);//重复long2
Long fakeLong=new LongParser().parseString(“20000”);//用false重复
System.out.println(“应为true:+(long2==equalLong));
System.out.println(“预期为false:+(fakeLong==equalLong));
}
}
C:\Documents and Settings\glowcoder\My Documents>javac Parser.java
C:\Documents and Settings\glowcoder\My Documents>javac IntParser.java
C:\Documents and Settings\glowcoder\My Documents>javac LongParser.java
C:\Documents and Settings\glowcoder\My Documents>javac ParserTest.java
C:\Documents and Settings\glowcoder\My Documents>java ParserTest
期待真实:真实
期望为假:假
我会保持对他们的管理,但会添加收集信息和向中央经理报告的方法。显然,您需要向解析器添加更多的方法来跟踪缓存。或者(这可能是一个更好的主意),您可以将缓存逻辑整合到一个缓存类中,并让管理器跟踪这些缓存

通过这种方式,您可以让缓存本身确定如何修剪其信息。它可以是最古老的,可以是大小,可以是各种各样的标准。也许它有用户信息,你希望你的付费用户更多地留在缓存中

import java.util.*;
class ParserCacheManager {

    private Set<Parser<?>> parsers = new HashSet<Parser<?>>();

    public void addParser(Parser<?> p) { parsers.add(p); }

    public int size() {
        int size = 0;
        for(Parser<?> p : parsers) size += p.cacheSize();
        return size;
    }

    public void trimToSize(int maxSize) {
        while(size() > maxSize) {
            Parser<?> p = largestParser();
            p.trimToPercent(0.90);
        }
    }

    /**
     * This would be better perhaps with a set sorted by
     * size, or something like that. But this works for example.
     */
    private Parser<?> largestParser() {
        Parser<?> largest = null;
        for(Parser<?> p : parsers) {
            if(largest == null || p.size() > largest.size())
                largest = p;
        }
        return largest;
    }

}
import java.util.*;
类ParserCacheManager{
私有集>();
public void addParser(Parser p){parsers.add(p);}
公共整数大小(){
int size=0;
for(Parser p:parsers)size+=p.cacheSize();
返回大小;
}
公共空间修剪大小(int maxSize){
while(size()>maxSize){
Parser p=largestParser();
p、 三倍体(0.90%);
}
}
/**
*如果有一个按排序的集合,这可能会更好
*大小,或类似的东西。但这是工作的例子。
*/
私有解析器largestParser(){
解析器最大=空;
for(解析器p:parsers){
如果(最大==null | | p.size()>最大的.size())
最大=p;
}
回报最大;
}
}

我将使缓存成为解析器的一部分。我肯定您会遇到某种编译错误,需要解决,但下面是我将要做的基本操作

import java.util.*;
abstract class Parser<T> {

    private Map<String,T> cache = new HashMap<String,T>();

    public final T parseString(String str) {
        T result = cache.get(str);
        if(result == null) {
            result = parseString0(str);
            cache.put(str,result);
        }
        return result;
    }

    protected abstract T parseString0(String str);

}

public class IntParser extends Parser<Integer> {

    protected Integer parseString0(String str) {
        return Integer.parseInt(str.trim());
    }

}

public class LongParser extends Parser<Long> {

    protected Long parseString0(String str) {
        return Long.parseLong(str.trim());
    }

}

class ParserTest {
    public static void main(String[] args) {
        Parser<Integer> intParse = new IntParser();
        Parser<Long> longParse = new LongParser();

        Long long1 = longParse.parseString("10000");
        Long long2 = longParse.parseString("20000");
        Long long3 = longParse.parseString("30000");
        Long equalLong = longParse.parseString("20000"); // repeat long2
        Long fakeLong = new LongParser().parseString("20000"); // repeated with fake
        System.out.println("Expecting true: " + (long2 == equalLong));
        System.out.println("Expecting false: " + (fakeLong == equalLong));
    }
}

C:\Documents and Settings\glowcoder\My Documents>javac Parser.java

C:\Documents and Settings\glowcoder\My Documents>javac IntParser.java

C:\Documents and Settings\glowcoder\My Documents>javac LongParser.java

C:\Documents and Settings\glowcoder\My Documents>javac ParserTest.java

C:\Documents and Settings\glowcoder\My Documents>java ParserTest
Expecting true: true
Expecting false: false
import java.util.*;
抽象类解析器{
私有映射缓存=新的HashMap();
公共最终解析字符串(字符串str){
T result=cache.get(str);
如果(结果==null){
结果=0(str);
cache.put(str,result);
}
返回结果;
}
受保护的抽象T parseString0(String str);
}
公共类IntParser扩展了语法分析器{
受保护的整数parseString0(字符串str){
返回Integer.parseInt(str.trim());
}
}
公共类长语法分析器扩展语法分析器{
受保护的长parseString0(字符串str){
返回Long.parseLong(str.trim());
}
}
类ParserTest{
公共静态void main(字符串[]args){
Parser intParse=新的IntParser();
Parser longParse=新的LongParser();
Long long1=longParse.parseString(“10000”);
Long long2=longParse.parseString(“20000”);
Long long3=longParse.parseString(“30000”);
Long equalLong=longParse.parseString(“20000”);//重复long2
Long fakeLong=new LongParser().parseString(“20000”);//用false重复
System.out.println(“应为true:+(long2==equalLong));
System.out.println(“预期为false:+(fakeLong==equalLong));
}
}
C:\Documents and Settings\glowcoder\My Documents>javac Parser.java
C:\Documents and Settings\glowcoder\My Documents>javac IntParser.java
C:\Documents and Settings\glowcoder\My Documents>javac LongParser.java
C:\Documents and Settings\glowcoder\My Documents>javac ParserTest.java
C:\Documents and Settings\glowcoder\My Documents>java ParserTest
期待真实:真实
期望为假:假
我会让他们保持现状,但我要补充一点
Cache<String, T> parsedObjectCache = CacheBuilder.newBuilder()
   .expireAfterAccess(10, TimeUnit.MINUTES)
   .build(
       new CacheLoader<String, T>() {
         public T load(String str) throws MyParseException {
           return parse(str); //called either on or from inside a Parser<T>
         }
       });