dwdyer / watchmaker Goto Github PK
View Code? Open in Web Editor NEWThe Watchmaker Framework for Evolutionary Computation
Home Page: https://watchmaker.uncommons.org
License: Apache License 2.0
The Watchmaker Framework for Evolutionary Computation
Home Page: https://watchmaker.uncommons.org
License: Apache License 2.0
Picking up on http://cvalcarcel.wordpress.com/2009/09/13/watchmaker-a-first-and-second-example/#comment-96 please consider adding support for Differential Evolution [1]. By all accounts it seems to produce optimal results much faster than Generic Algorithms and does not use the gradient of the problem being optimized so it can solve problems that GAs simply cannot.
Expected behavior: Download link should point to http://watchmaker.uncommons.org/download.php.
When using the GenerationalEvolutionEngine
is possible to get the List<EvaluatedCandidate<T>>
by running evolvePopulation
. Would it be possible to implement a similar interface on IslandEvolution, and perhaps reword it so it supports the EvolutionEngine
interface?
When using this framework with external evaluation code (that uses network or scripts written in another languages), it is crucial and very important to have ability to evaluate candidates in batches.
One of the examples of such need is when you're calling external script that have large "heating up" time (due to library loading, etc) that is larger than useful evaluation work that it does.
Another example is when your generational population data stored in network database and worker processes that evolve it are residing on different computers — so it's too expensive (time-wise) to transfer same populace-bound data for evolution of each candidate.
Hey, I just found out that the watchmaker framework uses the google-collection library which is deprecated.
The new google library is called guava.
EvaluatedCandidate class must not be final, because when implementing custom EvolutionEngine, users often want to associate additional data with each EvaluatedCandidate.
For example, if each candidate's fitness is compound fitness from several simulations, user may want (for reporting / logging purposes) store all fitness components in EvaluatedCandidate's custom inherited class.
Currently finality of EvaluatedCandidate & PopulationData classes prevents users from properly implementing custom EvolutionEngine.
Hi Dan,
I am am running into some design limitations of the EvolutionEngine classes. I'll try to explain my concrete problem to highlight the issue. My project requires a population of genetic programs to be run on a shared state such that all programs are executed in parallel for a couple thousand iterations before their fitness is known. Shared state access is done between the iterations and needs to be synchronized. The AbstractEvolutionEngine design can not support this, because it implements a different concurrency scheme. A program can not easily suspend the evaluation to let others execute until all have reached the synchronization point to do the shared state access and continue the evaluation. Apart from some ugly hacks to work around the problem a proper solution would require my own EvolutionEngine implementation to support my execution scheme. However, I would end up with a GenerationalSharedStateEvolutionEngine, SteadySharedStateEvolutionEngine and SharedStateEvolutionStrategyEngine. This suggests that the AbstractEvolutionEngine and its subclasses represent a coupling between the functionality needed to produce offspring and the execution scheme.
A more flexible approach that improves reusability would be to implement the different nextEvolutionStepmethods using a strategy pattern rather than the template method pattern. If you agree to this I could implement the necessary changes and send you a pull request.
The following piece of code makes sure that each mutation is done both as a decrement and an increment.
mutation *= -1; // Alternate between incrementing and decrementing. if (mutation == 1) // After gene has been both incremented and decremented, move to next one. { mutatedGene = (mutatedGene + 1) % Biomorph.GENE_COUNT; }
But if the 'Biomorph.GENE_COUNT' is 8 then the 9 Biomorphs will mutate genes 0, 1, -1, 2, -2, 3, -3, and 4. It will never mutate genes -4, 5, -5, 6, -6, or 7.
Regarding the page http://watchmaker.uncommons.org/manual/ch02s07.html (Using V0.7.1 from maven)
The Hello World example references "a brief pause" for computation and, later on, when an observer is attached there are only about 40 generations before a result is reached. However when I copy the code, it takes around 60 seconds @ 3.2GHz and generates 2M+ strings. Is this normal? I am trying to work out if I am doing anything wrong, but I am copying the code exactly, with no modifications.
I note that an increase of the population size to 1000 cuts the generations required to levels more like the example output, but the text does say that ten is definitely intentional.
PS. Minor note: On the same page - String result = engine.evolve(10, 0, new TargetFitness(11)); is a little out of date: the 0.7.1 requires a second argument to TargetFitness and there is a missing semi-colon after operators.add(new StringCrossover())
As I understand it, if elitism is a (legal) positive integer, then data.getBestCandidateFitness() should never decrease from generation to generation in my EvolutionObserver. I observe the best fitness fluctuating down as frequently as it goes up in my implementation. I'm pretty confident that my FitnessEvaluator is getting things right, consistently, as changing my evolution pipeline to include only the IdentityOperator returns the same value from generation to generation, meaning at least that the 'best' candidate is getting the same fitness evaluation.
Is there anything I could have written (candidate factory, evolution operators) besides the Fitness Evaluator that could cause data.getBestCandidateFitness() to decrease?
Or, is elitism (or my understanding of what it does) broken?
RandomDotOrgSeedGenerator (and by extension DefaultSeedGenerator) have a hard dependency on random.org . This is both ill-advised, as this opens a security avenue of attack, and causes problems on days when random.org is down, such as this morning.
This morning on Windows, GA optimization started failing with a NumberFormatException, because random.org output (this morning, only an error page) is attempted to be parsed as a number. This is a terrible idea. Java has built-in SecureRandom features, these should be used to generate random seeds on non-unix systems.
I cloned the repository and successfully built the sources.
However, on attempting to build the book, I received the following error(s):
C:\path-to-watchmaker\watchmaker>ant book
Buildfile: C:\path-to-watchmaker\watchmaker\build.xmlbook:
[mkdir] Created dir: C:\path-to-watchmaker\watchmaker\book\build
[uncommons:docbook] Making portrait pages on A4 paper (210mmx297mm)
[uncommons:docbook] WARN notifyFontReplacement, Font 'Symbol,normal,700' not f
ound. Substituting with 'Symbol,normal,400'.
[uncommons:docbook] WARN notifyFontReplacement, Font 'ZapfDingbats,normal,700'
not found. Substituting with 'ZapfDingbats,normal,400'.
[uncommons:docbook] Element include in namespace 'http://www.w3.org/2001/XInclud
e' encountered in book, but no template matches.
[uncommons:docbook] Error at xsl:text on line 112 of jar:file:/C:/path-to-watchmaker/watchmaker/lib/compilet
ime/uncommons-antlib-0.3.1.jar!/docbook-xsl/fo/docbook.xsl:
[uncommons:docbook] org.apache.fop.fo.ValidationException: Error(-1/-1): fo:bl
ock is not a valid child element of fo:root.BUILD FAILED
C:\path-to-watchmaker\watchmaker\b
uild.xml:234: java.lang.reflect.InvocationTargetException
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.
java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAcces
sorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.uncommons.antlib.tasks.docbook.DocBook.execute(DocBook.java:160)
at org.apache.tools.ant.UnknownElement.execute(UnknownElement.java:291)
at sun.reflect.GeneratedMethodAccessor4.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAcces
sorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.apache.tools.ant.dispatch.DispatchUtils.execute(DispatchUtils.jav
a:106)
at org.apache.tools.ant.Task.perform(Task.java:348)
at org.apache.tools.ant.Target.execute(Target.java:390)
at org.apache.tools.ant.Target.performTasks(Target.java:411)
at org.apache.tools.ant.Project.executeSortedTargets(Project.java:1399)
at org.apache.tools.ant.Project.executeTarget(Project.java:1368)
at org.apache.tools.ant.helper.DefaultExecutor.executeTargets(DefaultExe
cutor.java:41)
at org.apache.tools.ant.Project.executeTargets(Project.java:1251)
at org.apache.tools.ant.Main.runBuild(Main.java:809)
at org.apache.tools.ant.Main.startAnt(Main.java:217)
at org.apache.tools.ant.launch.Launcher.run(Launcher.java:280)
at org.apache.tools.ant.launch.Launcher.main(Launcher.java:109)
Caused by: javax.xml.transform.TransformerException: org.apache.fop.fo.Validatio
nException: Error(-1/-1): fo:block is not a valid child element of fo:root.
at com.icl.saxon.style.StyleElement.styleError(StyleElement.java:818)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
5)
at com.icl.saxon.style.LiteralResultElement.process(LiteralResultElement
.java:290)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLTemplate.expand(XSLTemplate.java:229)
at com.icl.saxon.style.XSLTemplate.start(XSLTemplate.java:202)
at com.icl.saxon.Controller.applyTemplates(Controller.java:297)
at com.icl.saxon.style.XSLApplyTemplates.process(XSLApplyTemplates.java:
139)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLTemplate.expand(XSLTemplate.java:229)
at com.icl.saxon.style.XSLTemplate.start(XSLTemplate.java:202)
at com.icl.saxon.Controller.applyTemplates(Controller.java:288)
at com.icl.saxon.style.XSLApplyTemplates.process(XSLApplyTemplates.java:
139)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.LiteralResultElement.process(LiteralResultElement
.java:290)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLTemplate.expand(XSLTemplate.java:229)
at com.icl.saxon.style.XSLTemplate.start(XSLTemplate.java:202)
at com.icl.saxon.Controller.applyTemplates(Controller.java:288)
at com.icl.saxon.Controller.defaultAction(Controller.java:313)
at com.icl.saxon.Controller.applyTemplates(Controller.java:278)
at com.icl.saxon.style.XSLApplyTemplates.process(XSLApplyTemplates.java:
139)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLIf.process(XSLIf.java:78)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLOtherwise.process(XSLOtherwise.java:48)
at com.icl.saxon.style.XSLChoose.process(XSLChoose.java:96)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLOtherwise.process(XSLOtherwise.java:48)
at com.icl.saxon.style.XSLChoose.process(XSLChoose.java:96)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLOtherwise.process(XSLOtherwise.java:48)
at com.icl.saxon.style.XSLChoose.process(XSLChoose.java:96)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
at com.icl.saxon.style.XSLTemplate.expand(XSLTemplate.java:229)
at com.icl.saxon.style.XSLTemplate.start(XSLTemplate.java:202)
at com.icl.saxon.Controller.applyTemplates(Controller.java:288)
at com.icl.saxon.Controller.run(Controller.java:220)
at com.icl.saxon.Controller.transformDocument(Controller.java:1125)
at com.icl.saxon.Controller.transform(Controller.java:994)
at org.uncommons.antlib.tasks.docbook.DocBookPublisher.createDocument(Do
cBookPublisher.java:166)
... 21 more
Caused by: org.apache.fop.fo.ValidationException: Error(-1/-1): fo:block is not
a valid child element of fo:root.
at org.apache.fop.fo.FONode.invalidChildError(FONode.java:435)
at org.apache.fop.fo.FONode.invalidChildError(FONode.java:420)
at org.apache.fop.fo.pagination.Root.validateChildNode(Root.java:126)
at org.apache.fop.fo.FOTreeBuilder$MainFOHandler.startElement(FOTreeBuil
der.java:271)
at org.apache.fop.fo.FOTreeBuilder.startElement(FOTreeBuilder.java:163)
at com.icl.saxon.output.ContentHandlerProxy.startElement(ContentHandlerP
roxy.java:129)
at com.icl.saxon.output.ProxyEmitter.startElement(ProxyEmitter.java:80)
at com.icl.saxon.output.NamespaceEmitter.startElement(NamespaceEmitter.j
ava:95)
at com.icl.saxon.output.GeneralOutputter.flushStartTag(GeneralOutputter.
java:745)
at com.icl.saxon.output.GeneralOutputter.writeContent(GeneralOutputter.j
ava:461)
at com.icl.saxon.output.GeneralOutputter.writeContent(GeneralOutputter.j
ava:444)
at com.icl.saxon.style.XSLText.process(XSLText.java:83)
at com.icl.saxon.style.StyleElement.processChildren(StyleElement.java:64
3)
... 60 moreTotal time: 3 seconds
After the most recent update, searching opens a separate search window in the app. However, neither window completes a search. It cycles back to the home screen.
Unable to search designs currently. Running on iPhone XR, app version 8.0.6
There seems to be the possibility that, when Runtime.getRuntime().availableProcessors() returns '1' that an exception occurs in the private constructor of the FitnessEvaluationWorker class. This is caused by 1 to be divided by 2, which is 0 in integers.
Suggested code correction:
int poolSize = Math.max(Runtime.getRuntime().availableProcessors() / 2, 1);
this.executor = new ThreadPoolExecutor(poolSize,//
poolSize, 60, TimeUnit.SECONDS,//
workQueue, threadFactory);
Hi! I'm currently building an island-based genetic calculations model and found a glitch with reproducibility.
Currently, the island engine passes the same random generator instance to each thread allocated for an island. Considering threads (code in the threads, actually) are naturally executed in an upredictable order (and so are random number picked from the rng), setting a seed on the rng have no desired effect - each program execution results are different.
I see two options actually:
The following program causes Swing to hang for me:
Main.java
import java.util.LinkedList;
import java.util.List;
import java.util.Random;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import org.uncommons.maths.random.MersenneTwisterRNG;
import org.uncommons.maths.random.Probability;
import org.uncommons.watchmaker.framework.*;
import org.uncommons.watchmaker.framework.factories.StringFactory;
import org.uncommons.watchmaker.framework.interactive.Renderer;
import org.uncommons.watchmaker.framework.operators.EvolutionPipeline;
import org.uncommons.watchmaker.framework.operators.StringCrossover;
import org.uncommons.watchmaker.framework.operators.StringMutation;
import org.uncommons.watchmaker.framework.selection.RouletteWheelSelection;
import org.uncommons.watchmaker.framework.termination.TargetFitness;
import org.uncommons.watchmaker.swing.evolutionmonitor.EvolutionMonitor;
public class Main
{
public static void main(String[] args)
{
// Create a factory to generate random 11-character Strings.
char[] chars = new char[27];
for (char c = 'A'; c <= 'Z'; c++)
chars[c - 'A'] = c;
chars[26] = ' ';
CandidateFactory<String> factory = new StringFactory(chars, 11);
// Create a pipeline that applies cross-over then mutation.
List<EvolutionaryOperator<String>> operators = new LinkedList<EvolutionaryOperator<String>>();
operators.add(new StringMutation(chars, new Probability(0.02)));
operators.add(new StringCrossover());
EvolutionaryOperator<String> pipeline = new EvolutionPipeline<String>(operators);
FitnessEvaluator<String> fitnessEvaluator = new StringEvaluator();
SelectionStrategy<Object> selection = new RouletteWheelSelection();
Random rng = new MersenneTwisterRNG();
EvolutionEngine<String> engine = new GenerationalEvolutionEngine<String>(factory,
pipeline,
fitnessEvaluator,
selection,
rng);
EvolutionMonitor monitor = new EvolutionMonitor<String>(new Renderer<String, JComponent>()
{
private final JLabel result = new JLabel();
@Override
public JComponent render(String entity)
{
result.setText(entity);
return result;
}
}, false);
engine.addEvolutionObserver(monitor);
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(monitor.getGUIComponent());
frame.setSize(800, 600);
frame.setVisible(true);
String result = engine.evolve(10, 0, new TargetFitness(11, true));
System.out.println(result);
}
}
StringEvaluator.java
import java.util.List;
import org.uncommons.watchmaker.framework.FitnessEvaluator;
public class StringEvaluator implements FitnessEvaluator<String>
{
private final String targetString = "HELLO WORLD";
/**
* Assigns one "fitness point" for every character in the
* candidate String that matches the corresponding position in
* the target string.
*/
public double getFitness(String candidate,
List<? extends String> population)
{
int matches = 0;
for (int i = 0; i < candidate.length(); i++)
{
if (candidate.charAt(i) == targetString.charAt(i))
++matches;
}
return matches;
}
public boolean isNatural()
{
return true;
}
}
If you modify the EvolutionMonitor renderer to return null Swing does not hang. I believe that the WatchMaker framework is "starving" the Swing thread somehow. If you add other EvolutionObservers that print to stdout the hang will disappear, again because the framework is spending less time inside the EDT.
Hey,
I'm working on simple example using multiple islands.
I have code as follows:
List<EvolutionEngine<FloatGenotype>> islands = new ArrayList<>();
Random rng = new MersenneTwisterRNG();
for(int i = 0; i < this.islands; i++) {
CandidateFactory<FloatGenotype> factory = new FloatGenotypeFactory();
List<EvolutionaryOperator<FloatGenotype>> operators = new LinkedList<>();
operators.add(new AverageFloatCrossover());
operators.add(new UniformFloatMutation());
EvolutionPipeline<FloatGenotype> pipeline = new EvolutionPipeline<>(operators);
FitnessEvaluator<FloatGenotype> evaluator = new FloatRastriginEvaluation();
SelectionStrategy<Object> strategy = new TournamentSelection(selectionPressureControl
.getNumberGenerator());
EvolutionEngine<FloatGenotype> engine = new GenerationalEvolutionEngine<>(factory, pipeline,
evaluator, strategy, rng);
islands.add(engine);
}
IslandEvolution<FloatGenotype> islandEvolution = new IslandEvolution<>(islands, new RingMigration(),
true, rng);
islandEvolution.addEvolutionObserver(monitor);
return islandEvolution.evolve(populationSize, // Population size per island.
20, // Elitism for each island.
50, // Epoch length (no. generations).
15, // Migrations from each island at each epoch.
terminationConditions;
Everything works fine when I'm setting populationSize on 120 or above. But if i try to use lower value i get following error on the end of first epoch, around 50th generation.
Exception in thread "main" java.lang.IllegalStateException: java.util.concurrent.ExecutionException: java.lang.IllegalArgumentException: Too many seed candidates for specified population size.
at org.uncommons.watchmaker.framework.islands.IslandEvolution.evolve(IslandEvolution.java:248)
at pl.agh.edu.evolution.experiment.Experiment.main(Experiment.java:104)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:483)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:140)
Caused by: java.util.concurrent.ExecutionException: java.lang.IllegalArgumentException: Too many seed candidates for specified population size.
at java.util.concurrent.FutureTask.report(FutureTask.java:122)
at java.util.concurrent.FutureTask.get(FutureTask.java:192)
at org.uncommons.watchmaker.framework.islands.IslandEvolution.evolve(IslandEvolution.java:220)
... 6 more
Caused by: java.lang.IllegalArgumentException: Too many seed candidates for specified population size.
at org.uncommons.watchmaker.framework.factories.AbstractCandidateFactory.generateInitialPopulation(AbstractCandidateFactory.java:66)
at org.uncommons.watchmaker.framework.AbstractEvolutionEngine.evolvePopulation(AbstractEvolutionEngine.java:135)
at org.uncommons.watchmaker.framework.islands.Epoch.call(Epoch.java:51)
at org.uncommons.watchmaker.framework.islands.Epoch.call(Epoch.java:27)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
I'm not setting seed candidates count or seeds candidates themselves so I guess error is not on my side. To be sure if it not dependent on elitism and migrations number I have lowered them to 5 and 3 respectively (as in user manual) but it has changed nothing. Still needed at least 120 objects in population to work.
Hey,
the link to the maven repository on the website seems to be outdated / broken http://watchmaker.uncommons.org/download.php
I guess this is not the right place to post this, but I did not find anywhere else to go :-)
Hi,
there is an argument missing in the example "Hello World" (page: http://watchmaker.uncommons.org/manual/ch02s07.html).
The Method 'targetFitness()' needs two arguments according to the api.
And consider to increase the elitecount (currently 0) .. of the "hello world" example. With an elitecount of 0 the evolution usually doesn't stop.
change:
String result = engine.evolve(10, 0, new TargetFitness(11));
to
String result = engine.evolve(10, 2, new TargetFitness(11, true));
thanks.
We can improve evolution performance of the AbstractEvolutionEngine
by exploiting the specified SelectionStrategy
behavior.
interface SelectionStrategy#select
comments:
... the same individual may potentially be selected more than once
This has a consequence in AbstractEvolutionEngine#evaluatePopulation()
which will then evaluate identical candidates more than once.
The result is reduced evolution performance which is a general problem not specific to any application.
One gets partial relief by maintaining the fitness value in the candidate itself (not something that is always possible) and evaluating conditionally. That requires synchronizing on the candidate in FitnessEvaluator#getFitness(). However, this scheme runs into thread contention problems with a high number of identical candidates, again resulting in reduced evolution performance.
The permanent solution is to only evaluate a reduced size set of distinct candidates. Synchronizing as described above is then no longer required.
So in AbstractEvolutionEngine#evaluatePopulation()
// Each entry contains the count of skipped duplicates (in addition to the 1st).
Map<T, Integer> duplicatesCountMap = new IdentityHashMap();
for (T candidate: population){
if(duplicatesCountMap.containsKey(candidate)){
duplicatesCountMap.put(candidate, duplicatesCountMap.get(candidate) + 1);
}else{
duplicatesCountMap.put(candidate, 0);
}
}
and then in both single threaded and multi-threaded if branches
replace
for (T candidate : population)
with
for (T candidate : duplicatesCountMap.keySet())
and then later some post-processing to add the skipped duplicates back to the results so that the population size remains the same (that is why we count the duplicates):
final List<EvaluatedCandidate<T>> skippedPopulation = new ArrayList<EvaluatedCandidate<T>>(population.size());
for(EvaluatedCandidate<T> evaluatedCandidate : evaluatedPopulation){
final Integer skippedCount = duplicatesCountMap.get(evaluatedCandidate.getCandidate());
for(int index = 0; index < skippedCount; index++){
skippedPopulation.add(evaluatedCandidate);
}
}
evaluatedPopulation.addAll(skippedPopulation);
Please refer to the attached source file
AbstractEvolutionEngine.zip
.
Hello Mr. Dyer,
First I wish to thank you for developing such a wonderful framework. It made my research so easy. I just had a quick question. How can I extend the Tournament selection strategy to involve more than two individuals? I am kind of new to this framework and any help will be greatly appreciated.
Thanks,
Vikas
Hello,
My fitness implementation, looks like:
fitness = surprise + efficiency
Efficiency is a value in an interval between 0 and 1.
However, the surprise value can assume any value great than zero (actually very big values can occur).
These two elements must to have the same weigh in equation and, to reach that, I have to normalize the surprise for current entire population before sum with efficiency value.
Do you have any idea to make this in the framework?
Thank you so much!
Live Long And Prosper
Celso França
Hi, I´am using watchmaker and I really like it, but I have got one little problem :( I want have time with LEDFont and in the background have text (88:88) with same font but smaller opacity. I design it at phone and it looking good on watch too. However later is time text at another position. It maybe 5px on the x position. Why is time changing position? I´am using 24 hour format.
Hi - I have tried setSeed method with org.uncommons.maths.random.MersenneTwisterRNG and it does not appear to work. When I use java.util.Random instead with the same code, the random sequence is reproducible (it is not with MersenneTwisterRNG). Perhaps I am misusing MersenneTwisterRNG?
Here is a snippet of code:
// Random rng = new MersenneTwisterRNG();
Random rng = new Random();
rng.setSeed(44);
When java.util.Random is used, randomness is reproducible. When MersenneTwisterRNG is used, randomness is not reproducible.
Another note: on the watchmaker api docs (http://watchmaker.uncommons.org/api/index.html), MersenneTwisterRNG is not listed, nor is org.uncommons.maths.random package. Any advice is appreciated.
Hi there,
just came back to see what's new and noticed there's a broken link in the "Getting Started" section of the Watchmaker main page.
Look for "download the latest version of the Watchmaker Framework".
Regards
Stefan
I am having problem running the examples.
Using Mac OS java version "1.6.0_20"
Java(TM) SE Runtime Environment (build 1.6.0_20-b02-279-10M3065)
Java HotSpot(TM) 64-Bit Server VM (build 16.3-b01-279, mixed mode)
downloaded ant, source code of watchmaker, build without any problem
but when I am trying to run java watchmaker-examples-0.7.2.jar
here's the error msg
watchmaker-framework-0.7.2 kiddo$ java watchmaker-examples-0.7.2.jar
Exception in thread "main" java.lang.NoClassDefFoundError: watchmaker-examples-0/7/2/jar
Caused by: java.lang.ClassNotFoundException: watchmaker-examples-0.7.2.jar
at java.net.URLClassLoader$1.run(URLClassLoader.java:202)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
at java.lang.ClassLoader.loadClass(ClassLoader.java:307)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:301)
at java.lang.ClassLoader.loadClass(ClassLoader.java:248)
There's some possible reuse of that class, but can't be even instantiated because it is package private. Any reasons for that?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.