-
-
Save shemnon/6b37047bac73c8da55f7 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/*======================================================================*\ | |
ICBIaW50OiBtYWtlIHRoaXMgYXMgY2xvc2UgdG8gcHJvZHVjdGlvbi1yZWFkeSBzb3VyY2 | |
UgY29kZSBhcyB5b3UgY2FuIQ0KICANCiAgQm9udXMgcG9pbnRzIGZvciB0ZWxsaW5nIHVz | |
IHdoYXQgdGhpcyBkb2VzOg0KDQogICAgJycuam9pbihpdGVydG9vbHMuY2hhaW4oKnppcC | |
hzWy0yOjotMl0sIHNbOjotMl0pKSkNCg0KPj4gSXQgcmV2ZXJzZXMgdGhlIHN0cmluZyBp | |
biBwYWlycy4gIA0KPj4gSWYgdGhlIHN0cmluZyBpcyBvZGQgbGVuZ3RoIHRoZW4gdGhlIG | |
ZpcnN0IGNoYXJhY3RlciBpcyByZXZlcnNlZC4gIFRoZW4gZWFjaCBjaGFyYWN0ZXIgaXMg | |
cGFpcmVkLCB0aGVuIHRoZSBwYWlycyBhcmUgcmV2ZXJzZWQuDQoNCiAgKlN1cGVyKiBib2 | |
51cyBwb2ludHMgZm9yIGZpbmQgdGhlIGJ1ZyBpbiB0aGlzIGNvZGU6DQogIA0KICAgIGh0 | |
dHA6Ly9wYXN0ZS5wb3VuZC1weXRob24ub3JnL3Nob3cvdTE2eFVSS1JGWnVOaHdzV214SU | |
IvDQoNCj4+IEkndmUgbmV2ZXIgdXNlZCB0aG9zZSBsaWJyYXJpZXMsIGJpdCBpdCBsb29r | |
cyB0byBtZSBhdCBsaW5lIDcgcHl0aG9uIGlzIGF0dGVtcHRpbmcgdG8gZ2V0IGEgd3JpdG | |
UgbG9jayBvbiB0aGUgQ09VTlQgdmFyaWFibGUsIGFuZCB0aGUgb3RoZXIgdGhyZWFkcyBh | |
cmUgaG9sZGluZyBhIGxvY2sgb24gdGhhdCB2YXJpYWJsZS4gIFRvIGZpeCBpdCB3ZSBzaG | |
91bGQgdXNlIGEgY29uY3VycmVudCBmcmllbmRseSBhY2N1bXVsYXRvciBvbiBDT1VOVC4= | |
\*======================================================================*/ | |
import java.lang.ref.ReferenceQueue; | |
import java.lang.ref.WeakReference; | |
import java.util.List; | |
import java.util.concurrent.ConcurrentSkipListSet; | |
import java.util.stream.Collectors; | |
import java.util.stream.IntStream; | |
class Id { | |
static final ConcurrentSkipListSet<Integer> _all_ids = new ConcurrentSkipListSet<>(); | |
public Id(final int id) { | |
this._my_id = id; | |
boolean inserted = _all_ids.add(id); | |
assert inserted; | |
new WeakReference<>(this, theseIDs).enqueue(); | |
} | |
public void cleanUp() { | |
if (! this._cleaned) { | |
_all_ids.remove(this._my_id); | |
_cleaned = true; | |
} | |
} | |
static ReferenceQueue<Id> theseIDs = new ReferenceQueue<Id>(); | |
static { | |
Thread t = new Thread(() -> { | |
while (true) { | |
try { | |
Id id = theseIDs.remove().get(); | |
if (id != null) { | |
id.cleanUp(); | |
} | |
} catch (InterruptedException ie) { | |
// intrruptions are so rude! | |
} | |
} | |
}); | |
t.setDaemon(true); | |
t.start(); | |
} | |
private int _my_id; | |
private boolean _cleaned = false; | |
public static void main(String... args) { | |
List<WeakReference<Id>> weakIDs = IntStream.range(0, 5_000) | |
.mapToObj(Id::new) | |
// .peek(id -> { int[] i = new int[5000];}) | |
// .peek(id -> { | |
// assert !id._cleaned; | |
// System.out.println(_all_ids.size()); | |
// }) | |
.map(id -> new WeakReference<>(id)) | |
.collect(Collectors.toList()); | |
// simulate long running app | |
System.gc(); | |
System.gc(); | |
// likely all weak references collected, expect zero | |
System.out.println(_all_ids.size()); | |
} | |
} |
Are you interested in the project, or just having fun? :o)
Meaning those two options are mutually exclusive?
The header in the gist lacks a e-mail adders to send this info to. A google search of this gist goes to a bunch of job boards and some freelance sites I haven't made accounts for, but no e-mail as per the instructions.
Is this an UntraCoin project or a bitcoin project?
ping me at [email protected]
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Four problems I see:
(1) the _all_ids list was an instance variable when it should have been static to be shared across all instance
(2) hash set is not MT safe. Use a concurrent class instead. This particular one has nice performance characteristics for Integers since they are order able.
(3) The bug most people stop at: you never add the ID to the list of all IDs.
(3.1) Flair: add an assert in case we re-use IDs. a variable and class name of ID implies uniqueness.
(4) Finalize? Really? That has some entirely unreliable performance characteristics. Instead I enqueue the objects in a reference queue so that the cleanup is done when the object is garbage collected, not some point after the garbage collection.