Pattern regex Java: compilare costanti di tempo o membri di istanza?


13

Attualmente, ho un paio di oggetti singleton in cui sto facendo corrispondenze su espressioni regolari e i miei Patternsono definiti in questo modo:

class Foobar {
  private final Pattern firstPattern =
    Pattern.compile("some regex");
  private final Pattern secondPattern =
    Pattern.compile("some other regex");
  // more Patterns, etc.
  private Foobar() {}
  public static Foobar create() { /* singleton stuff */ }
}

Ma l'altro giorno mi è stato detto da qualcuno che questo è un cattivo stile, e che Patterns dovrebbe sempre essere definito a livello di classe, e invece dovrebbe assomigliare a qualcosa del genere:

class Foobar {
  private static final Pattern FIRST_PATTERN =
    Pattern.compile("some regex");
  private static final Pattern SECOND_PATTERN =
    Pattern.compile("some other regex");
  // more Patterns, etc.
  private Foobar() {}
  public static Foobar create() { /* singleton stuff */ }
}

La durata di questo particolare oggetto non è così lunga, e la mia ragione principale per usare il primo approccio è perché non ha senso trattenermi Patterndopo aver ottenuto GC.

Qualche suggerimento / pensiero?

Risposte:


18

Gli oggetti Java Pattern sono thread-safe e immutabili (sono i matcher che non sono thread-safe).

Pertanto, non vi è motivo di non crearli staticse verranno utilizzati da ciascuna istanza della classe (o di nuovo in un altro metodo nella classe).

Rendendole variabili di istanza, non importa quanto breve (o lungo) il loro tempo di vita significhi che stai ricompilando l'espressione regolare ogni volta che crei un'istanza di una classe.

Uno dei motivi principali di questa struttura (Pattern essendo una fabbrica per oggetti Matcher) è che la compilazione dell'espressione regolare nei suoi automi finiti è un'azione moderatamente costosa. Tuttavia, si scopre che spesso la stessa espressione regolare viene utilizzata più e più volte in una determinata classe (tramite invocazioni multiple dello stesso metodo o punti diversi nella classe).

D'altra parte, il Matcher è piuttosto leggero: indica lo stato del pattern all'interno del Pattern e la posizione all'interno della matrice di caratteri per la stringa.


Per un singleton , non dovrebbe importare troppo , perché dopo tutto, c'è solo un'istanza di esso che si trova in giro e non stai ricreando il singleton ancora e ancora (aspetta, 'la vita del singleton non è così lunga' ? Questo significa che lo stai istanziando più volte nel corso dell'applicazione?)

Tuttavia, scoprirai che alcuni analizzatori di codice sorgente statici non riconoscono che qualcosa è un singleton e si lamenteranno che stai creando istanze di modelli da costanti per ogni istanza della classe.

Il problema con tutto ciò è che non è una buona scelta (non è male neanche per un singleton) e potresti iniziare a ignorare altri avvisi per cose di cui ti parlano il compilatore e gli strumenti di analisi (leggi di più sulle finestre rotte ).

Relazionato:


Risposta fantastica - sì, intendevo dire che è stata creata / utilizzata solo una volta, e una volta che non rientra nell'ambito di applicazione, viene eseguita per sempre. Grazie per la lettura di follow-up!
yamafontes,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.