Not logged in.  Login/Logout/Register | List snippets | | Create snippet | Upload image | Upload data

130
LINES

< > BotCompany Repo | #1027374 // CleanFluidTextFile

JavaX fragment (include) [tags: use-pretranspiled]

Libraryless. Click here for Pure Java version (5188L/34K).

sclass CleanFluidTextFile implements Runnable {
  srecord Entry(S text, SS params) {
    long targetIndex;
    S actualText() { ret unquote(text); }
  }

  // set by user
  int maxRefLength = 8;
  bool verbose;
  Reader reader;
  Writer writer;
  
  // set by class
  new L<Entry> entries;
  new Map<S, Entry> relocationMap;

  long maxFileSize() {
    ret rangeOfNHexNumberWithNDigits(maxRefLength);
  }
  
  run {
    read();
    write();
  }
  
  void read ctex {
    Producer<S> tokenizer = javaTok_onReader(reader);
    FluidTextFileEntry entry;
    while ((entry = readFluidTextFileEntry(tokenizer)) != null) {
      if (!containsKey(entry.params, "_")) // not a deletable entry
        entries.add(new Entry(entry.quotedContent, entry.params));
    }
    if (verbose) pnlStruct(entries);
  }
  
  void write ctex {
    // make a map and pessimistically assign byte indices to all entries

    for (Entry e : entries)
      mapPut(relocationMap, e.params.get("i"), e);
    makeIndices(entries);

    // rewrite references

    for (Entry e : entries)
      if (hasReferences(e))
        e.text = replaceRefs(e, r -> lookupInRelocationMap(r));

    // write out

    long idx = 0; // index into file
    for (Entry e : entries) {
      assertEquals(e.targetIndex, idx);
      e.params.put("i", renderReference(e.targetIndex));
      S line = entryToString(e, idx);
      if (verbose)
        print(quote(line));
      writer.write(line);
      int l = lUtf8(line);
      if (verbose)
        print("Actual entry length: " + l);
      idx += l;
    }
  }

  S lookupInRelocationMap(S ref) {
    Entry e = relocationMap.get(ref);
    //print("lookupInRelocationMap: " + ref + " => " + e);
    ret e == null ? null : renderReference(e.targetIndex);
  }

  S renderReference(long idx) {
    ret takeLast(maxRefLength, longToHex(idx));
  }

  void makeIndices(L<Entry> entries) {
    long idx = 0; // index into file
    for (Entry e : entries) {
      e.targetIndex = idx;
      int l = pessimisticEntryLength(e);
      idx += l;
      if (verbose)
        print("Pessimistic entry length: " + l);
    }
  }

  S entryToString(Entry e, long idx) {
    ret entryToString(e, renderReference(idx));
  }
  
  S entryToString(Entry e, S idx) {
    SS params = litorderedmap(
      i := idx,
      l := intToHex_flexLength(lUtf8(e.text)));
    mapPutAll_noOverwrite(params, e.params);
    ret renderEqualsCommaProperties(params) + " " + e.text + "\n";
  }  

  S dummyRef() {
    ret rep('0', maxRefLength);
  }

  bool hasReferences(Entry e) {
    ret eq(e.params.get("refs"), quote("at *"));
  }

  int pessimisticEntryLength(Entry e) {
    Entry e2 = e;
    if (hasReferences(e)) {
      e2 = cloneObject(e);
      e2.text = replaceRefs(e, r -> dummyRef());
      if (verbose)
        print("Pessimistic: rewrote text to " + quote(e2.text));
    }
    S s = entryToString(e2, dummyRef());
    if (verbose)
      print(quote(s));
    ret lUtf8(s);
  }

  S replaceRefs(Entry e, IF1<S> f) {
    LS tok = javaTokWithUnifiedNumbersAndIdentifiers(e.actualText());
    for (int i : jfindAll(tok, "at *")) {
      S x = f.get(tok.get(i+2));
      if (nempty(x))
        tok.set(i+2, x);
    }
    ret multiLineQuote(join(tok));
  }
}

download  show line numbers  debug dex  old transpilations   

Travelled to 7 computer(s): bhatertpkbcr, mqqgnosmbjvj, pyentgdyhuwx, pzhvpgtvlbxg, tvejysmllsmz, vouqrxazstgt, xrpafgyirdlv

No comments. add comment

Snippet ID: #1027374
Snippet name: CleanFluidTextFile
Eternal ID of this version: #1027374/19
Text MD5: ffa4dfe811c003225ea49771acaee792
Transpilation MD5: b13db51370e86a00e50eebeda216e009
Author: stefan
Category: javax / io
Type: JavaX fragment (include)
Public (visible to everyone): Yes
Archived (hidden from active list): No
Created/modified: 2020-03-15 17:11:10
Source code size: 3353 bytes / 130 lines
Pitched / IR pitched: No / No
Views / Downloads: 263 / 667
Version history: 18 change(s)
Referenced in: [show references]