yourplotlib
Best practices for domain-specific matplotlib libraries
Colin Carroll, Hannah Aizenman, and Thomas Caswell
Introduction: Plotting should understand your domain
This essay is based on a talk given on November 5, 2019 at PyData New York. Original slides are available here. All the code for producing the plots is available on in this repo. It is (of course) produced with matplotlib, with gracious assists from NumPy, SciPy, and Project Jupyter.
There is a tension in matplotlib between being a library and an application. A library seeks to provide stable and useful APIs for application builders, while an application tries to "do the right thing". You can think of this essay as some steps towards using matplotlib productively as a library to build applications for your own domain or data.
There are numerous popular libraries that already follow this advice:
- ArviZ for plotting Bayesian data Colin is one of the creators of ArviZ, while Hannah and Thomas are maintainers of matplotlib. Two years of interaction between a domain-specific author and general purpose maintainers is what inspired this talk/essay.
- Seaborn for statistical data visualization
- plotnine, an implementation of a
grammar of graphics The R library ggplot2 helped popularize the grammar of graphics in
the data science world. The codebase for plotnine is also remarkably clean and worth a read
if you are trying to do anything tricky and custom with
Artist
s. DataFrame.plot
(pandas) andDataArray.plot
(xarray) for labelled arrays- basemap Deprecated in favor of cartopy, cartopy, and geoplot for geospatial data
- scikit-learn has a new plotting API that works closely with domain-specific objects
- grave and nxviz for network data
A more complete and up-to-date listing of 3rd party packages is on the matplotlib website Pull requests welcome and encouraged!.
1. Stylesheets
Whether you are in a lab setting, a data science team, open source project, or individual writing blog posts, perhaps the easiest thing to do is to make a custom stylesheet. This takes less than an hour and can be reused forever. Think of it as marketing for your visualizations: a consistent and distinctive style can help you stand out and be memorable.
Many styles already ship with matplotlib, and you can try using one out right now. The default stylesheet matplotlib uses has 10 colors it cycles through that were carefully picked, and will be applied if you do nothing.
import matplotlib.pyplot as plt plt.style.use('default')
You can restore an older, "classic" matplotlib style that uses 7 colors, outlined markers, and larger figures:
plt.style.use('classic')
The ggplot2
theme has become quite recognizeable, and ships with matplotlib. Notice the
light gray background and subtle white axes One of the first statistics (and programming, and
visualization) lectures Colin ever attended was as a graduate student at Rice University, and was
given by Prof. Hadley Wickham on his new library ggplot2. He
also gave the specific advice to customize your theme to be anything but the default, and
indeed the ggplot2 default theme was quite striking!.
plt.style.use('ggplot')
The style that the writers and dava visualization team at FiveThirtyEight use is also quite distinctive. Notice the bold colors and thick lines, which are ideal for display graphics, if harder to use for exploratory visualizations.
plt.style.use('fivethirtyeight')
Colin uses a custom stylesheet So the following code will only work if you first install his stylesheet. heavily inspired by Edward Tufte In fact, translating the CSS that this essay also uses into matplotlib styles., as well as by the Altair Another implementation of the grammar of graphics, based on Vega and Vega-Lite. library, which also uses the hollow circles as a default marker.
plt.style.use('tufte')
Experimenting with stylesheets
We can look at one way of interactively building a custom styling. We do this by updating the
rcParams
object, which behaves like a dictionary. First, we make some standard plot that
looks generally like the sorts of plots we want to deal with.
plt.plot(*np.random.randn(50, 2))
First, we adjust the default size for the figure. This is designed for talks and essays, so a wide, not-very-tall figure is appropriate.
plt.rcParams.update({ plt.rcParams.update({ "figure.figsize": [10.0, 3.0], }) plt.plot(*np.random.randn(50, 2))
Now we can update colors. This talk was delivered at PyData New York, and we can imagine we are building a domain-specific library for making plots for PyData conferences. The easiest thing we can do is take these distinctive colors from the PyData logo as our default colors:
plt.rcParams.update({ "axes.prop_cycle": plt.cycler( "color", ["#EE9041", "#459DB9", "#667B83"]), }) plt.plot(*np.random.randn(50, 2))
Next, we update the default marker from None
to a diamond, again borrowing from the
PyData motif:
plt.rcParams.update({ "lines.marker": "d", }) plt.plot(*np.random.randn(50, 2))
We can remove the lines, so that by default we get a scatterplot instead of a line plot
plt.rcParams.update({ "lines.linestyle": "", }) plt.plot(*np.random.randn(50, 2))
Then making the markers bigger, so we can actually see them Note we are cheating and adding
clip_on=False
here, which lets our markers get drawn outside the axis limits..
plt.rcParams.update({ "lines.markersize": 48.0, }) plt.plot(*np.random.randn(50, 2), clip_on=False)
Removing the bounding box (called spines
), as well as the axis ticks on
the bottom and the left gives this a more artistic look. Note while we are doing this that we could
instead
leave some subset of the spines visible, or move the axis ticks to the top or right of a plot.
plt.rcParams.update({ "axes.spines.bottom": False, "axes.spines.top": False, "axes.spines.left": False, "axes.spines.right": False, "xtick.major.bottom": False, "ytick.major.left": False, }) plt.plot(*np.random.randn(50, 2), clip_on=False)
Finally, for some artistic flair and pop, we add a thin outline to the markers:
plt.rcParams.update({ "lines.markeredgecolor": "black", }) plt.plot(*np.random.randn(50, 2), clip_on=False)
This is now a stylish default! Note that it helps us create a certain kind of plot with minimal code. Whether or not this is the kind of plot you want is up to you.  A few
parameterss need special care to encode in the format, but it is reasonably easy to pattern match. See
the FiveThirtyEight
stylesheet or Colin's custom
stylesheet for examples of the format.
To find where to save this stylesheet, you use the "stylelib" directory in your matplotlib configuration directory. You can find the location of this by running
from pathlib import Path print(Path(matplotlib.get_configdir()) / "stylelib")
On my computer, I have a file at ~/.config/matplotlib/stylelib/tufte.mplstyle
, which
lets me run
plt.style.use("tufte")
and be all set.
There are also ways to pip
install styles, so you can distribute custom stylesheets using
Python packaging. One way is to follow ArviZ's approach, and
add your stylesheet directory to matplotlib's search path on import:
# __init__.py from matplotlib.pyplot import style # add ArviZ's styles to matplotlib's styles arviz_style_path = os.path.join(os.path.dirname(__file__), "plots", "styles") style.core.USER_LIBRARY_PATHS.append(arviz_style_path) style.core.reload_library()
Wrap common plots in functions
Our goal is to ease and encourage the use of plots, and after updating stylesheets, it is easy to start writing small functions implementing default behavior.
def confetti(N, *, ax=None, **kwargs): if ax is None: ax = plt.gca() my_artists = ax.plot(*np.random.randn(N, 2), clip_on=False, **kwargs) return my_artists
A few notes on this function:
- The
*
in the arguments is a Python 3 feature that requires the user to supply exactly one positional argument:confetti(10, ax)
throws an error, whileconfetti(10, ax=ax)
works. - The block that handles
if ax is None:
will get the current axes or create a new one. If we had wanted, we could have always created new axes usingplt.subplots()
. Calling plot on a pandasSeries
usesplt.gca
while aDataFrame
usesplt.subplots
. This is a domain-specific choice! - We pass on keyword arguments other than
ax
to the underlying matplotlib function. - The function returns all the Artists added to the axes, for the user to customize.
We might also implement a more general version of the curvy plot from above:
def solitare(x, *, ax=None, **kwargs): if ax is None: ax = plt.gca() kwargs.setdefault('clip_on', False) my_artists = ax.plot(x, np.cos(x), x, np.sin(x), x, -np.cos(x), **kwargs) return my_artists
Now we can use these plots in three ways:
On their own:
confetti(42)
On the same axes:
confetti(20, marker="*", markersize=50) confetti(87, markersize=10)
On multiple axes:
fig, (ax1,ax2) = plt.subplots(nrows=2) solitare(np.linspace(-np.pi, np.pi), ax=ax1, markersize=30, marker='$\infty$') confetti(13, ax=ax2, marker='>')
Build Custom Plots with Artist
s
Sometimes your goal visualization requires more customization or performance than the high level
functions that matplotlib provides. This is where we start accessing functions from matplotlib the
library, rather than the application. Specifically, we will be using built-in
Artist
s, which are the building blocks functions like plot
and
scatter
are already using.
As an example of a custom functionality we may need, Colin is a fan of his dog He thinks it is important you know that his name is Pete, and that he is a good boy. and of hacking on images. We want to convert an image like this
To one like this
You can see the code in the attached Python file, but there is a step The process ends up looking like this: We convert to grayscale Create a blurred mask of white and black rows Pointwise multiply the grayscale image (which is just a numpy array of intensities) with the smooth mask Threshold the image, setting pixels darker than a certain level to black, and the rest to white Divide into regions, and calculate how wide our lines should be at every x-position Convert the image into lines of varying width (for which we need custom functionality!) Make the lines wider, so it looks nicer Smooth out the line widths, using a smoothing kernel where we need to make a line (in fact 30 lines) with a width that varies. This is not built into matplotlib, so we will build it ourselves.
Using LineCollection
to build a custom plot
First, we find the LineCollection artist, and see that it allows multiple lines with mapped colors.
Next, we see how it works:
fig, ax = plt.subplots() lc = LineCollection( segments=[ ((0, 1), (1, 1), (2, 1), (3, 1)), # flat line ((0, 1), (1, 2), (2, 3), (3, 4)), # straight line ((0, 0), (1, 2), (2, 4), (3, 9)), # parabola ]) ax.add_collection(lc) ax.set_ylim(0, 9) ax.set_xlim(0, 3)
We notice a few things about the API:
- Initializing the class returns an instance, and we use
ax.add_collection(...)
to add this artist collection to the axes. - We then also manually set the axis limits.
This is going to be more fine-grained control, and we will have to be more specific about what we plot.
Now we can apply some styles to the lines:
... lc = LineCollection( segments=..., colors=('red', 'green', 'blue'), linewidths=(4, 8, 12), linestyles=('dashed', 'dotted', 'solid') ) ...
This is not quite what we want: each line has a separate style applied to it. What if instead, we make our single line out of a bunch of lines of length 1?
... lc = LineCollection( segments=[ ((0, 0), (1, 2)), ((1, 2), (2, 4)), ((2, 4), (3, 9)) ], ... ) ...
This looks like what we want! Notice that we used the endpoint of one segment as the start point of the next segment. But four points of a parabola is boring: how do we scale this up?
... x = np.linspace(-2, 2) y = x ** 2 points = np.vstack((x, y)).T # array([[-2. , 4. ], # [-1.91836735, 3.68013328], # [-1.83673469, 3.37359434], # [-1.75510204, 3.08038317],... segments = list(zip(points[:-1], points[1:]))
We create an \(N \times 2\) matrix of points on our line, and zip it with itself, offset by 1. This gives us the same sort of data as we had before: a list of \(N - 1\) "lines" of length 1, where the end point of one is the start point of the next. Putting this together, we can plot this:
fig, ax = plt.subplots() lc = LineCollection(segments=segments) ax.add_collection(lc) ax.set_ylim(-0.2, 4) ax.set_xlim(-2, 2)
Looking better! But we want to change linewidths along the length of this. We can do that by just passing a vector of the same length as the x-data:
linewidths = 30 * np.abs(np.sin(10 * x)) ... lc = LineCollection( segments=segments, linewidths=linewidths ) ...
While we are at it, we can edit other styles like color as well:
cmap = plt.get_cmap('viridis') ... lc = LineCollection( segments=segments, linewidths=linewidths, colors=cmap(np.abs(np.sin(5 * x))), ) ...
Make light wrappers for your use!
To keep pushing a point, you should make small functions and wrappers to make these plots easier for yourself and for others: your plotting should understand your domain. Here is the function to implement the flexible line plotting API we were just exploring:
def plot_line(x, y, linewidths=None, colors=None, ax=None): points = np.vstack((x, y)).T segments = list(zip(points[:-1], points[1:])) if ax is None: ax = plt.gca() lc = LineCollection( segments=segments, linewidths=linewidths, colors=colors, ) ax.add_collection(lc) # ...mess with scales... return lc
Note we used the pattern from earlier with plt.gca()
. This is not much code, but it enables
lots of exploration. We can play around with other parametric plots and be creative like with the
parabola earlier. Here is a Möbius strip:
t = np.linspace(0, np.pi * 2.0, 2_000) cmap = plt.get_cmap('twilight') colors = cmap(np.abs(np.cos(t * 1.25))) plot_line(np.cos(t), np.sin(t), # circle linewidths=40 * np.cos(1.5 * t), # 3 turns colors=colors) ax.axis('off')
We can also go back to our motivating example with Pete the pup, and try out the control we also have over color now:
Conclusion: Build the interface you need
Your plotting should understand your domain, and there are many levels at which this understanding can take place. In rough order of depth:
- Use a stylesheet to create a distinctive, consistent look.
- Write wrappers around
ax.plot
,ax.scatter
,ax.hist
, and the like to build the API you want. - Write your own functions that instantiate
Artist
s likeLineCollection
. - Write your own
Artist
classes that reimplementdraw
We did not cover implementing a custom Artist here, since it is a much bigger topic than a 30 minute talk. This is very powerful, and very flexible. See grave for an example of this..
Matplotlib is an active library, and is interested in helping science advance, and helping you better visualize your data Or dog.. In particular,
- If you need help packaging your plotting library or stylesheet to be pip-installable, reach out! Packaging is hard, and we want you to succeed.
- If you have other general questions, join the discussion on matplotlib's new discourse.
- Share what you build, if you are comfortable! A twitter account shares beautiful plots, the third party package listing spreads the word of domain-specific libraries, and of courseissues and pull requests may be filed.


I've been taking this for a month, I've never had acne before and now I do, I get really depressed and have breakdowns, I've been spotting for almost two weeks, and I've put on weight that is hard to lose!!!!
I have stomach cramps every few days and sometimes really bad migraines, I hate these pills!!
SENT2


Player {{playerInvited}} has invited you to join their lobby!
{{#if roomIsPublic}} Public {{else}} Invite-only {{/if}}
Join a lobby by inviting players or accepting an invite
Users Online: {{usersOnlineCount}}


Gather Login and General Information
The main workshop is happening on the Gather.town platform. This platform provides a 2d layout in which participants can navigate an avatar using the arrow keys. When a group of avatars are in close proximity, a video conference is started. Members of such a group can also share screen to, e.g., go over slides from the talks. The following is a brief guide to the experience.
- Access: https://www.virtualchair.net/gather/MD4SG
- Authentification: authenticate with the email address that you registered with
- Tech troubleshooting<EMAIL_ADDRESS>- MD4SG '20 gather venue map: Coming Soon
- Social events guide: /workshop/MD4SG20/Social-Events.pdf
- Need more help<EMAIL_ADDRESS>Zoom Logistics
Overview:
All oral presentations, keynote speeches and panels will take place on Zoom. Access to the Zoom room will be via gather. In case you have issues with this, please reach out to us.
Live Translation:
This year we are glad to provide real-time interpretaiton between English and Spanish for plenary talks and our panel session. To familiarize yourself with Zoom's interpretation feature, please take a look at this guide
Gather Guide
Setting Up:
We strongly recommend that you give yourself at least a 30 minute margin to enter Gather for the first time. There can be last minute issues when entering the platform, and this way you can ensure you won't miss any workshop events/presentations.
Moving your avatar:
Once you enter Gather, you will take control of an avatar, which you can move around the workshop venue with your arrow keys.
Further Gather logistics:
The guide below contains further details for how to navigate Gather, including how to control interaction distance, how to locate people, how to have private video conversations, how to screenshare, public and private chat etc.


Description :
The registration for the contest shall take place on the spot at
the venue.
There shall be multiple rounds. The nature such rounds shall be decided
by the organizers.
Each team shall comprise of 3 to 6 members.
The scoring system of each round shall be intimated to the participants
during the contest.
The winners shall be decided on the basis of the points earned through the
rounds.
The decision of judges and coordinators are final and biding in all cases


And along similar lines to the afp548.com article on this, Greg Neagle written a similar piece describing how he’d use it in his environment (and it even has screenshots …).
Using managed preferences in the local DS domain on Macs
Longer article up at AFP548.com, but basically I’ve been playing around a fair bit with MCX in DSLocal lately, and there are a lot of interesting applications….
It’s so nice to be able to just manage plists now…. NetInfo I miss you not at all.
Post Macworld 2008
So my webhost managed to mess up all htacess files and thus lock me out of my blog for a couple of weeks. I considered briefly posting via MySQL, but then dragged myself back into the realm of the sane and just waited it out. Apologies to the comments that were awaiting moderation…. My resolution is to actually blog more this year, so I’ve started trying out MarsEdit to see if being able to work offline improves the situation….
Another Macworld is over. To be honest, this one was a bit too hectic to really enjoy as a pure punter, and besides, I missed what was a brilliant match where India broke Australia’s record equalling winning streak in Perth.
Schoun Regan and I did the two day PowerTools conference on Advanced OS X Server, then Jeff McCune and I did a shorter presentation and demo on Puppet that seems to have provoked some interest in the MacEnterprise crowd.
The few other talks I managed to make it to were quite good, even given the difficulty of catering to the very wide range of technical ability in a Macworld crowd… I thoroughly enjoyed Andrina Kelly’s Lucid System Administration presentation, some of our Google techs were inspired by Kevin White’s Neutered Admins talk, and I heard lots of good reports about Greg Neagle and Philip Rhinehart’s System Imaging and Deployment two day session.
The two highlights of the week for me were firstly that Joel managed to work the optical inch into his Directory Services talk. Nice work….
Secondly would have to have been seeing Devo in the flesh. Thanks to Dave Pugh (you need to get that blog going Dave…), I now have much better photos than my mediocre camera gave….
Devo were simply awesome. I was prepared to have all my illusions shattered… but they put on an awesome performance….
Wrapping ‘defaults’ to be more flexible…
So I don’t know about any of you, gentle readers, but ‘defaults’ really gives me the shits sometimes.
Exhibit A:
/ $ defaults read /Library/Preferences/com.apple.loginwindow.plist 2007-11-21 13:12:04.288 defaults[97501:10b] Domain com.apple.loginwindow.plist does not exist / $ defaults read /Library/Preferences/com.apple.loginwindow (snip actual working output)
Exhibit B:
/ $ cd /Library/Preferences /Library/Preferences $ defaults read ./com.apple.loginwindow.plist 2007-11-21 13:13:24.327 defaults[97540:10b] Domain ./com.apple.loginwindow.plist does not exist /Library/Preferences $ defaults read ./com.apple.loginwindow 2007-11-21 13:13:25.799 defaults[97546:10b] Domain ./com.apple.loginwindow does not exist
This really annoys me, that ‘defaults’ firstly doesn’t accept the full path to the plist, when other tools like ‘launchctl’ do, and requires that you strip off the “.plist” from the end, and secondly, that you can’t use relative paths.
This annoyed me so much that I decided to finally do something about it. This function resolves both problems.
function defread { defaults read $(echo "$@" | sed "s|\./|`pwd`/|g" | sed "s|.plist||g"); }
And now we can do:
/ $ defread /Library/Preferences/com.apple.loginwindow.plist / $ cd /Library/Preferences /Library/Preferences $ defread ./com.apple.loginwindow.plist
or even:
/Library/Preferences $ defread ./com.apple.loginwindow.plist SHOWFULLNAME 1
mmmm.
My first earthquake….
So last night I experienced my first earthquake ever….
Considering it was a 5.6 and quite close to our house, I’m a little disappointed now that it wasn’t more dramatic… nothing even fell off the shelves. Just several huge thumps that felt like something dropped from a great height into the backyard.
Not to give any impression I didn’t freak out … On the other hand, Chantal having grown up in Tokyo was calm and collected.
I see Bill Baumgarter felt it too...
InstaDMG beta released…
Full props to Josh for getting this out there….
Seriously though, this is how imaging has to be done these days for Macs. Given that we have all these excellent tools now, and given that Apple keep messing us around by releasing hardware that isn’t quite compatible with the latest OS X point update and requires a specific kext or whatever… it’s just too much pain to manage monolithic images by hand anymore.
Creating stable and unstable branches with Apple’s Software Update Server.
SirAdmin source code.
So I really thought I’d done this before… but I’ve had someone want to try and actually work on SirAdmin, and I hadn’t published the source code.
Â You can download the source here.
I really have no time to work on it at the moment, and there really isn’t an itch to scratch since I started work at Google. (what? You thought I could use it to admin Gmail? ;)
It’s the BSD licence, feel free to do anything with it other than recoil too badly in horror at the nasty code.Â I think it needs refactoring, but go crazy. I’d like to know about any derivative works btw, but that’s not essential.
New article on afp548.com
In response to some queries on the os x server mailing list, I’ve put up a new article on afp548.com with a script that will automatically disconnect disabled/asleep AFP sessions that have been idle over a certain time threshold.
Best to comment over there.
E-3 Visa Experience…
So after finding Andrew Pollock’s blog entry and Yasser Hamed’s info incredibly useful, I thought I may as well post some updates on a slightly more recent E-3 visa application experience.
For those of you who don’t know, the E-3 visa is a US visa that is only open to Australian residents. It’s essentially the same as the H-1B visa, apart from the fact that your spouse can also work in the US, it’s indefinitely renewable, and so far at least, you can’t apply for the green card while in the US on an E-3.
There’s a nice summary available on the Sydney US Consulate site. Things may be different with other companies, but Google seem to be rather familiar with the whole process and pretty much organised everything I needed. The two things that seem mandatory for the company sponsoring you to provide are a statement in support of your application and a Labor Condition Application approved by the US Dept of Labor, which is normally used for the H-1B applications. It looks like the bureaucracy has caught up with the existence of the E-3 now and it’s actually an option on the form, so you no longer need the company to scrawl E-3 across the top of it.


---
layout: archive
title: Lean Prover Zulip Chat Archive
permalink: 144837PRreviews/78935781fractionmap.html
---
The archive URL format has changed. Please find this page at:
https://leanprover-community.github.io/archive/stream/144837-PR-reviews/topic/.23781.20fraction_map.html


This page provides information relevant to the methods of managing the
processing of personal data of users who log in Chiara Ferragni
Collection Website (the following “User” or “Users”)
that can be found at the address
www.chiaraferragnicollection.com
(hereinafter the “Website”). It is information given in
compliance with art. 13 of the Law Decree of 30
th June 2003,
no. 196, “Code for protecting personal data” (hereinafter
“Privacy Code”).
1. Personal Data Collector
The Data Collector is Serendipity Srl (hereinafter only
“Serendipity” and/or the “Collector”), with
offices at via Melone 2, 20121 Milano.
2. Purposes of the processing and type of personal
details
The personal details that the User voluntarily provides when he/she
logs in to the Website, such as name, surname, password, addresses,
phone numbers, e-mail addresses, tax code, VAT number, credit card,
bank details may be used by the Collector for the following
purposes:
i)
registration and orders management, which means managing the User’s
logging into the Website and dealing with the User’s orders
and/or providing services relevant to the orders such as, for
example, the creating of a “Wish List”;
ii)
newsletter subscription, which means managing User’s
subscription to the newsletter service by Chiara Ferragni
Collection, automatically receiving every new issue or newsletter
and other commercial and promotional communications for free;
iii)
profiling purposes, which means processing profiles based on the
preferences and the purchases of the User in order to send
information focused on the User’s interests and needs.
The User‘s provision of data for the purpose of registering
with the Website and order processing, as set out in the above
point a), is necessary to perform the obligations under the contract
with the User and/or to fulfil the specific requests of the same,
and therefore the Holder does not require the User’s express
consent for processing the data. Failure to provide the data
required for the purposes set out in the above point a), however,
will mean that the User will not be able to register with the
Website, manage or process any orders or be provided with the
related services, including, but not limited to, the creation of a
“Wish List”.
With reference to the purposes of subscribing to the newsletter
and profiling, as set out in the above points b) and c), the
provision of data is optional and processing of the same by the
Holder can only be carried out with the User ‘s specific and
express consent. The User’s refusal to the processing of the
data for the purposes set out in the above points b) and c), means
that the Holder will not be able to process the data supplied for
the purposes of subscribing to the newsletter and profiling, but it
is still possible for the User to register with the Website, manage
or process any orders or be provided with the related services,
including the creation of a “Wish List”.
Please take note that pursuant to art. 130, paragraph 4, of the
Privacy Code, the Collector may use the details relevant to the
e-mail that the User has provided during the sale of a product or
the supply of a service, for offering services similar to those that
are subject of the sales and without getting the User’s
authorization. At any moment, the User can refuse the processing of
data easily and free of charge by following the methods given in the
paragraph 5 “Rights of the concerned person.”
3. Method to process the data
The User’s data is processed mainly by means of electronic
systems and sometimes in hardcopies.
The User’s data will be kept with a method that allows the
identification for the time strictly necessary to achieve the
purposes for which the data is collected and processed and, in any
case, in accordance with law provisions.
The Collector and the responsible part have adopted suitable security
measures in accordance with the law to prevent the loss of Data,
unauthorized access or improper or illegal uses.
The User’s data may be transferred to foreign countries (also
extra-EU countries, such as USA), in compliance to the
above-mentioned information.
4. Categories of subjects to whom the personal data can be
communicated or who can know it and the diffusion of personal
data
In order to achieve the purposes that the personal data is collected
for, the Collector can appoint other responsible parties for
processing the personal data such as IT service providers, i.e.
direct marketing, internet service and cloud computing, subjects
that are in charge of the warehouse logistics, as well as promotion,
sale and delivery of the products and services of the Collector,
customer care, companies and other subjects that provide customers
with legal, fiscal, accountancy, financial, technical-organization,
data processing and communication services. Subjects that provide
bank services, i.e. financial, insurance and credit recovery
services, controlled companies, subsidiaries, public authorities and
supervising bodies.
In order to get the complete list of subjects responsible for
personal data processing, the User can contact the Collector in
accordance with the methods given in the following section 5 “Rights
of the concerned persons”.
For the same purposes, Chiara Ferragni Collection and the parties
responsible for processing can appoint other responsible parties for
processing data such as employees in charge of the execution of
orders, the customer care, the IT and marketing services (if the
authorization is given), the IT systems and management systems of
the Website and the technical and commercial personal in charge of
providing the website services.
No User’s personal data collected from this website will be
diffused.
5. Right of the concerned person
Pursuant to art. 7 of the Privacy code, the Users can, at any time,
request information about their personal data, if it exists, its
contents, origin, correctness or ask for its integration and update
or correction. In accordance with the same article, the User is
entitled to request its deletion, transformation in an anonymous
form or the block of his/her data which is processed in violation of
the law and, in any case, the User can, for legitimate reasons,
oppose himself/herself to its processing.
In order to exercise the above mentioned rights, the User can send a
request to Serendipity Srl., the Data Collector, by:


I just noticed that there is no strrstr()
function in the standard C library.
I needed that for a project, using ANSI-C. So I wrote it.
Here's the code, maybe it can be helpfull for someone else... :
char * strrstr( char * s1, char * s2 ); char * strrstr( char * s1, char * s2 ) { char * ss1; char * sss1; char * sss2; if( *( s2 ) == '\0' ) { return s1; } ss1 = s1 + strlen( s1 ); while( ss1 != s1 ) { --ss1; for( sss1 = ss1, sss2 = s2; ; ) { if( *( sss1++ ) != *( sss2++ ) ) { break; } else if ( * sss2 == '\0' ) { return ss1; } } } return NULL; }


I had the incredible opportunity to spend 10 weeks working for Zillow as a software engineering intern in
summer 2020. I learned many new skills, both technical and non-technical, and collaborated with my team using
Agile Practices.
This involved daily stand-ups, bi-weekly sprint planning/demo/retrospectives,
and using Jira for Kanban with my team.
Accomplishments:
-
I provided application performance monitoring (APM) features for some of ZG's micro-services using
Datadog's APM platform and their APIs.
I integrated Datadog into our micro-services by creating bash scripts and implementing GitLab's pipeline functionality
to automate the creation and maintenance of Datadog's dashboards and monitoring features.
This gave the team I was with transparency on the health and performance of their micro-services
while automating a lot of the work they would need to do otherwise to maintain Datadog features.
This was my main project that lasted from the second week of my internship to the end.
-
I coordinated with UI/UX and DevOps teams to include a new feature in our service that will allow automatic,
hands-off sending of emails to recipients based on triggered events.
I synchronized with a different team who are are responsible for maintaining their service that's used
to automate the process of sending emails.
This involved learning quickly about their service in order to
create email templates (written HTML) and modify configuration files (HOCON) as needed to integrate
my team's service with theirs.
For my team's service, I wrote Java code to extract data from JSON files, fetched from GraphQL, which are
used to populate placeholders in the email templates with personalized information relating to the recipient
before sending an email out.
-
I participated in a company-wide hack-week with my team to develop a dynamic website that provides non-technical
admins a web-interface to view and manage sensitive information stored in MySQL and DynamoDB databases.
I designed and developed a web-page, and this involved using React for the first time. Since we only had
two days to work on the project, I quickly learned how to use the React framework along the
way.
I recycled an existing react component and modified as needed to satisfy the new requirements.
This involved writing code (JavaScript) to create listeners and event handlers, based on user events,
that executes HTTP requests for existing services that were responsible for querying the databases in
order to acquire or manipulate data.
This also involved coordinating with the team to determine what data to expose to the user and
designing the interface itself in a user-friendly format.
-
I performed other trivial tasks to help me learn more about micro-services architecture and
CI/CD practices including:
-
Supporting deployment of several micro-services from development to stage environments.
-
Wrote missing unit tests on existing code with JUnit 5 to achieve 100% test coverage.
I had the opportunity to teach kids from ages 13 and below about 4th generation technology and basic
programming fundamentals for the summer of 2019.
Some of the subjects taught include mobile and 3D game development, minecraft artificial intelligence, and
virtual reality.
I gave my students a head start on understanding core programming concepts
such as variables, functions, conditional logic, object-oriented programming principles, and data structures.
Check out their website:
www.codeexplorers.org
I worked and continue to work as a part time student assistant for a Junior-level programming course.
My duty is to evaluate and grade programs written in Java.
I inspect and evaluate their code visually and carefully for correct functionality, readability, and quality.
I'm also responsible for spotting and assessing signs of plagiarism, such as finding nigh-identical code across multiple submissions,
and communicating my concerns with the professor.
After assignments are graded and submitted, I also take the additional step to provide feedback to help students
improve, going as far as to debug their code if they couldn't find the bug themselves.


Hello! I'm Gustavo Paludeti A graphic designer from Belmont, CA with a passion for skateboarding, fishing, and motorsports. All throughout my life i've been inspired by nature and the people around me to create art and pursuit design. I am eager to learn and explore different realms of design.
650.787.0307
GUSPALUDETI650@GMAIL.COM


Triage
Normalize is split into multiple repositories. Most of these repositories can be found within the Normalize GitHub organization. When requesting features or reporting bugs, please try to open an issue in the correct repository.
- discussions - a repository for any general discussions. Don't know where to open an issue? Want to ask for support? Open an issue here.
- normalize.github.io - this Normalize.IO homepage and documentation
- proxy.js - the normalization proxy
- nlz - the command line
nlz(1)
utility - transforms.js - all the transforms supported by both the proxy and
nlz(1)
- The Polyfills Organization - for anything having to do with browser support, polyfills, and transpilation
URL Shorthands
Typing https://nlz.io/
everywhere becomes tedious quickly,
so Normalize allows you to use shorthands for dependencies.
Shorthands simply expand to the long Normalize URLs.
However, due to the wide remote support Normalize provides,
shorthands require a certain degree of specificity.
However, shorthands can only be used if:
- You use a build process,
nlz build
- You use a Normalizer server such as
koa-normalize
- You use a custom client-side ES6 module loader
Thus, shorthands are second-class citizens. Normalize will eventually provide a custom module loader for these shorthands.
The Law of Shorthands
- You shan't use shorthands in CSS and HTML as they do not allow custom loaders.
- You shan't use shorthands in libraries, only applications where you can expect a custom module loader to be used. Creating libraries with shorthands is too vendor-specific. URLs should always work in any environment!
@
is used for versions and commits. Do not use#
.
Shorthands
Extensions
Files that end with /
expand to /index.js
:
./lib/ => ./lib/index.js
Files that do not end with .js
simply have .js
appended:
./index => ./index.js
npm
<EMAIL_ADDRESS>resolves to https://nlz.io/npm/-/<module>/<version>/<file...>
:
emitter@1 => /npm/-/emitter/1/index.js
emitter@1/ => /npm/-/emitter/1/index.js
emitter@1/something => /npm/-/emitter/1/something.js
Namespaces are prefixed with @<org>
,
i.e<EMAIL_ADDRESS>:
@nlz/emitter@1 => /npm/nlz/emitter/1/index.js
@nlz/emitter@1/ => /npm/nlz/emitter/1/index.js
@nlz/emitter@1/something => /npm/nlz/emitter/1/something.js
When prefixed with @org
, the @<version>
is optional:
@nlz/emitter => /npm/nlz/emitter/*/index.js
@nlz/emitter/ => /npm/nlz/emitter/*/index.js
@nlz/emitter/something => /npm/nlz/emitter/*/something.js
npm shorthands may always be prefixed with npm:
:
npm:emitter@1 => /npm/-/emitter/1/index.js
GitHub
<EMAIL_ADDRESS>resolves to https://nlz.io/<user>/<project>/<version>/<file...>
:
component/emitter@1 => /component/emitter/1/index.js
component/emitter@1/lib => /component/emitter/1/lib/index.js
Note that @<version>
here is required for the shorthand,
otherwise it could be a file.
Everything Else
All other remotes can be abbreviated to:
<EMAIL_ADDRESS>Where:
remote
is the remote name or alias.user
is optional if the remote has a global namespace (i.e.npm
)project
- the name of the project/module/packageversion
- is optional, defaulting to*
file
- can be completely empty, defaulting to/index.js
Some remotes, such as npm, have or will have namespaces. However, it will be treated as if it does not as most modules do not use namespaces. As you can see from above, npm modules have a custom shorthand syntax due to this pecularity.
nlz(1)
nlz(1)
is the stopgap CLI tool for normalization proxies.
Eventually, nlz build(1)
will be completely optional,
and nlz(1)
will primarily be a CLI tool for inspecting your app/component's dependency tree.
Installation
Currently, you must install nlz(1)
with npm(1)
:
npm install -g nlz
nlz(1)
supports node v0.10+,
but you should use node v0.11+ for better performance
as generators are extensively used in the source code.
Be sure to globally install any transforms you'd like to use as well.
npm install -g jade marked
normalize-manifest.json
When building, a normalize-manifest.json
file is created.
Be sure to add this file to your .gitignore
!
This JSON file is used for various purposes:
- You can use this to inspect all the files in the build as well as its
dependency tree.
nlz(1)
uses this file in other commands, such asnlz-dependencies(1)
, to help inspect the files and the dependency tree. - You may use this file to create your own SPDY push server or middleware.
nlz build, nlz watch
These are the primary build command. You may think of it as browserify's build command with multiple entry point support as well as CSS and HTML file support.
Most of these parameters and options can be set via .nlzrc
,
allowing developers to simply run nlz build --watch
.
Note that the builder does not support buildilng web components! This is essentially impossible to do. Only use web components in a SPDY environment.
Entry Points
nlz build [entrypoints...]
// will build to build/index.js and build/index.css, respectively
nlz build client/index.js client/index.css
-
If you are only building a single entry point, you can
stream the result through stdout
with the -
option:
nlz build index.js - > index.built.js
Stdin is not supported.
--out, -o
The destination folder, defaulting to build/
.
The destination file will be the same name as the entry point's file name.
nlz build client/index.js --out public
--watch, -w
Watch the source files for changes and rebuild automatically.
You should use this as rebuilds are fast and incremental.
Simply loading nlz(1)
takes a considerable amount of time,
especially if you use a lot of transformations.
nlz build client/index.js --watch
This is aliased as nlz watch
.
--standalone, -s
Create a standalone, UMD-wrapped JS bundle.
nlz manifest
Similar to nlz-build(1)
,
except no files will actually be built.
Use this just to create normalize-manifest.json
,
which is required for the dependency inspection commands.
--no-min, -M
By default, nlz-manifest(1)
calculates the minified size of assets.
This gives each file a better representation of its size
in the final bundle.
However, this takes a long time compute.
Set --no-min
to disable minified size calculations.
nlz dependencies
List all the dependencies, included nested ones, of a single entry point. Unlike other "ls" type commands, this command does not create an incredibly nested tree. The file size is listed next to each file.
nlz dependencies <entrypoint>
// list the dependencies of a single file
nlz dependencies index.js
--remotes, -r
By default, dependencies of remote dependencies are not traversed.
To include them, use the --remotes
option.
nlz dependents
This command is similar to nlz-dependencies(1)
,
except shows all the nested dependents of a particular file.
Any file included in the manifest could be used as an entry point.
nlz dependencies <entrypoint>
// list all the nested dependents of<EMAIL_ADDRESS>nlz dependents<EMAIL_ADDRESS>nlz duplicates
Lists all remote dependents of which you use more than a single version. In frontend development, you don't want duplicate dependencies as it means unnecessary bandwidth usage.
// list the duplicate dependencies
// based on the current normalize-manifest.json
nlz duplicates
nlz-duplicates(1)
will show:
- The "redundancy size", or the estimated bytes you could save by de-duping each dependency.
- Each version of the dependency used.
- Each file of each dependency used, it's size, and its dependents.
nlz size
List the sizes of an entry point and its dependencies, as well as its combined size. Useful for gauging which dependency is the largest.
nlz size <entrypoint>
// get the size of test/index.js and its dependencies
nlz size test/index.js
--exts, -e
Filter the files by a comma-separated list of extensions. For example:
nlz size -e js,css,svg test/index.js
--threshold, -t
Only show files larger than a threshold
file size.
For example, only list files larger than 1kb
:
nlz size -t 1kb test/index.js
nlz graph
Create a graph of your dependency tree. Run nlz graph -h
for more details.
.nlzrc
.nlzrc
is an optional JSON configuration file for local environments.
It's completely optional.
You may have a global, .nlzrc
configuration for your computer as well as local .nlzrc
configuration for each app.
For example, you might want to point all your requests to a proxy on your network instead of https://nlz.io.
.entrypoints
The entry points for the build.
This allows you to not specify the entry points every time you run nlz build(1)
.
{
"entrypoints": ["client/index.js", "client/index.css"]
}
You may also use objects if you want to set custom options on each entry point:
{
"entrypoints": {
"client/index.js": {
},
"client/index.css": {
}
}
}
.proxy and .self-signed
{
"proxy": "localhost:8888",
"self-signed": true
}
This is to set a custom proxy other than https://nlz.io.
proxy
should be the full host, including the port.
Set self-signed
to true
if the proxy is using a self-signed certification,
otherwise an error will be thrown.
Remember, proxies must always use SSL.
.minifiedLength = true
Option whether to include each file's minified length in the manifest.
This takes a long time to calculate,
so is only recommended when you do --watch
.
Set to false
if you never want to calculate this.
.directory = "repositories"
{
"directory": "/User/jong/.repositories"
}
By default, all files are stored to process.cwd() + '/repositories'
.
Thus, every app or component you work on will have its own directory
folder.
This may be less than ideal for you as you'll have multiple copies.
You may optionally set this directory to a global directory like ~/.repositories
so that every app or component you work on share the same files.
It will also make installations a little faster.
.transform = "normalize-transforms"
Use a custom transform function instead of those supplied by Normalize. See normalize-transforms for more information.
.transforms = {}
Pass options to the transform function mentioned above, which is normalize-transforms.
.manifest = "normalize-manifest.json"
This allows you to use a custom normalize-manifest.json
file name.
Transforms
These are all the transforms available for both the normalization proxy and nlz-build(1)
.
Unlike other bundlers and build systems, adapters transforms are included automatically. There are a couple of reasons for this:
- This middleware system is a more complicated than other middleware systems:
- The use of Koa-based upstream/downstream is quite complex
- Order of middleware is very important
- Transforms are not orthogonal to another, so we have to make sure each plugin interacts with each other well.
- The purpose of normalization is for everyone to be on the same page. It's counter productive to have different semantics for the same transform across applications.
However, for both the proxy and for nlz(1)
,
you must install each underlying library yourself.
If all libraries were included,
then nlz(1)
will quickly grow to 100mb+
as well as have a very long install time
due to all the C/C++ addons these libraries use.
For example, to use the Jade transform, you must also install Jade globally:
# Install Normalize
npm i -g nlz
# Install Jade as well
npm i -g jade
PRs for additional transforms are welcomed as long as there's a valid use-case and people would actually use it. Feel free to create feature requests and pull requests in the transform.js repository.
How Transforms Work
Given a source file such as template.html
,
the walker transforms the file based on additional .<extensions>
.
For example, template.html.js
will export the HTML string as a JS string.
This is superior to other transform systems because:
- It's compatible with HTTP servers
- The transforms used are explicitly shown
- It allows you to use the same source file in multiple ways without configuration
For example, template.jade.js
returns a jade render function whereas template.jade.html.js
returns the jade template as a compiled string.
You can also compose multiple transforms together.
For example, .jade.html.js
is a composition of .jade.html
and .html.js
.
Unlike other build systems,
transforms have the ability to inject dependencies into your application and automatically install them,
making development easier in general.
For example, to use .jade.js
, you need the jade runtime.
The Jade transform will automatically inject the runtime by compiling your jade template to something like this:
import jade from 'https://nlz.io/github/visionmedia/jade/1/lib/runtime.js'
export default function template(locals) {
// compiled jade
}
CSS Transforms
less.css
Convert LESS files to CSS.
@import 'styles.less.css';
(sass|scss).css
Convert SASS files to CSS.
@import 'styles.sass.css';
@import 'styles.scss.css';
stylus.css
Convert Stylus files to CSS.
@import 'styles.styl.css';
JS Transforms
.<mime:text/*>.js
All extensions whose corresponding MIME type is text/*
are automatically transformed to a JS string using JSON.stringify()
unless superceded by another transform.
import text from 'something.txt'
var el = document.createTextNode()
el.textContent = text
.json.js
Transforms JSON files to a JS object.
import data from 'data.json'
var name = data.name
.coffee.js
Transforms a CoffeeScript file to JS.
import fn from 'thing.coffee'
fn()
Template Transforms
.jade.html
Compile jade templates to an HTML string.
For example, combined with the .<mime:text/*>.js
transform:
import html from 'template.html'
el.innerHTML = html
.jade.js
Compile jade templates to a function.
import render from 'template.jade'
import data from 'data.json'
el.innerHTML = render(data)
.(md|markdown).html
Compile markdown templates to an HTML string using marked.
Note that without .html
, the actual markdown is returned.
import html from 'article.md.html'
el.innerHTML = html
.jsx.js
Compile React .jsx
templates to JS.
.html.domify.js
Compile an HTML string to an element using domify. This is useful for web components and templates.
import template from 'template.html.domify'
document.body.appendChild(template.cloneNode(true))
Normalization Proxy
This is the public HTTP API for https://nlz.io as well as any normalize-proxy. If you're interested in setting up your own proxy, consult the normalize-proxy repository itself.
URL Structure
All URLs have the form:
https://nlz.io/<remote>/<user>/<project>/<version>/<file...>
Different proxies will have different hostnames.
The version
and file
may not be included in some end points.
Protocol
Every proxy must serve via HTTPS and SPDY/HTTPv2, even with a self-signed certificate. The primary reason is that some browsers intend to not support SPDY without SSL.
Remote
A supported remote's name, for example github/
.
Aliases will also be supported and will simply redirect to the canonical short name.
For example, github.com
and raw.githubusercontent.com
would redirect to github
.
User
The owner of a repository.
If the remote does not have a namespace, the user should simply be -
.
https://nlz.io/npm/-/escape-regexp/*/index.js
Project
The name of the project/module/component.
Version
Any version as defined by http://semver.org.
You should not include leading v
s and =
in single versions otherwise a redirect will occur.
Versions can also be git branches and commit SHAs if the remote is accessed via git and will redirect to the full commit sha.
API End Points
GET File
You may still GET
files directly, even with transforms.
All of the files' dependencies will be SPDY pushed to the client.
A redirect may be returned as a response.
If this is the case, the redirect location will be SPDY pushed as well.
Each file can have the following query strings.
These are only valid when exact, so don't include a trailing =
.
Only one query string can be used at a time:
?source
- return/redirect the source file and its dependencies all without any transformations applied. Useful for building server-side.
If any of these query strings are included, then all the pushed dependencies will also include the same query string.

For non-git remotes, this will check for the latest version of the project and install it locally.
You may consider this the optional "publish" step of Normalize.IO.
GET versions.json
GET https://nlz.io/<remote>/<user>/<project>/versions.json
Will return an array of versions that are currently available on the proxy.
If no versions are installed,
a 404
and an empty array will be returned.
If you pushed a new version of a package,
but the proxy has not installed it yet,
simply install it by hitting the pull
entry point or GET
any file.
Note: he semantics of this endpoint is subject to change. In particular, it should return all available versions on the remote.
GET proxy.json
GET https://nlz.io/proxy.json
Returns relevant information about the proxy including hostname, version, and supported remotes.
GET polyfill.js
Creates a polyfill bundle based on the client's user agent. See polyfills/polyfills for more details.
Normalization
Packages are "normalized" based on these JSON files in descending priority.
component.json
package.json
This is particularly important if you compile your module for one package manager but not the others.
Thus, if you have to compile your module for a package manager,
compile it for bower
.
package.json
Only npm
and github
-style dependencies are supported.
Only semantic versions are supported - versions that have weird suffixes will be ignored.
Other types of dependencies such as tarballs will be ignored.
Circular Dependencies
Modules that must be normalized and have circular dependencies are not supported.
In fact, these modules may actually mess up the proxy.
Please don't create circular dependencies!
Use devDependencies
or something instead.


Swag - O - Meter
Does your selfie with hashtag #technicalteamsolutions have enough swag?
Find out now!
Fork me on GitHub.


GraphingCalc
Please select your math subject:
Calculus
Multivariable Calculus
Please enter your function:
Enter


Select skills to contribute, skills to learn, and civic interests.
Project Match will connect you to civic projects.


Aim is to boost private investment, says CEA
‘Corporate tax rate cut will help’
by PTIChief Economic Adviser Krishnamurthy Subramanian on Monday said private investment was the key to economic growth and the recent cut in corporate tax rate was done to boost investments.
“Private investment is the driver of economic growth. Steps that we are taking, be it corporate tax rate cut, be it code on wages and industrial relations, is to try and create a more favourable environment for investment,” Mr. Subramanian said at the FICCI Young Leaders Summit here.
He said investment was required for sustained economic growth. “So, there is indeed well-thought out agenda in implementing these measures; the effects of these will show, ” he said.
India’s GDP growth slowed sharply to 4.5% in the July-September, hit by a slump in manufacturing output. The pace had moderated from 5% in April-June and 7% in the July-September quarter of 2018.
In September, the Centre slashed the corporate tax rate to 22% from 30%. It also lowered the tax rate for new manufacturing companies to 15% to attract new foreign direct investments.


Towards an algorithmic cinema
new project that I find very exciting will occupy me throughout the next twelve months. Thanks to the Conseil des Arts et des Lettres du Québec and the Plan culturel numérique du Québec, I will have the opportunity to do research about digital art—and more specifically, about algorithmic cinema: an experimental animation cinema (most often abstract, but not necessarily so), that is created by writing code to generates images and movement.
Because this cinema is somewhat unknown to the general public and practiced by relatively few artists around the world, I hope to help in demystifying it by maintening a journal of my work during this project. The journal will contain short experimental animations and parts of the creative process—so, a mixture of things that are accessible to all and other things that are more technical or “arcane”, like blocks of code and mathematical formulas. We’ll see how this joyous aggregate ends up looking.
Free software
sing and releasing free software will be an important facet of this projet. Everything I create as part of my research will be released under free licences, so anyone will be free to distribute it, to modify it, and to distribute modified versions of it. The main licences that I will use are the Free Art Licence 1.3, the Gnu Gpl 3.0 Licence and the Apache 2.0 Licence.
Additionally, the software and the learning material around which my research will be articulated will be either free or gratis. I will apply many things learned from a small set of online courses (often called “moocs”, for “massive online open courses”). Here are the courses in question:
- — Introduction to Complexity, by Melanie Mitchell.
- — Introduction to Agent Based Modeling, by William Rand.
- — Algorithms on Graphs, by Daniel Kane.
- — Introduction to Dynamical Systems and Chaos, by Dave Feldman.
- — Machine Learning for Musician and Artists, by Rebecca Feibrink.
- — Intelligence and Learning, by Daniel Shiffman.
A first example
ommencing right away with a first experiment is the best thing to do. The drop caps that you see in this article (the big ornate letters at the beginning of each section of text) were created with a semi-algorithmic method. The letters themselves were hand-drawn using a program I created, and then the root-like patterns surrounding the letters were generated with an algorithm called diffusion limited aggregation. Here is a visualization of this algorithm in action:
Diffusion limited aggregation is relatively simple to explain: the animation above is divided on a grid, and each cell of this grid can either be “awake” or “sleeping”. Any other metaphor could be used. People often talk of live cells and dead cells, but I prefer to let my cells fall asleep and wake up. What matters is that the cells can be in two different states. An awake cell has a colour, and a sleeping cell is black. Between each frame of animation, thousands of invisible ants walk randomly on the grid. Ants can only travel on sleeping cells. When an ant arrives on a cell that has one or more awake neighbours, it awakens the cell where it is currently standing, and then it vanishes. The newly awaken cell is then coloured. That’s it!
The remarkable thing about diffusion limited aggregation is that such a simple system, based largely on randomness (the paths of the walking ants are completely random), is able to generate a distinctly structured pattern. The pattern resembles the roots or the branches of a tree—they have a certain fractal quality, a notion that will be very important for many of my upcoming experiments.
Here is a visualization of this algorithm when it is applied on a grid where a single cell, situated in the middle, is initially “awake”:
I’ll also add that the microscopic “film grain” that is subtly visible in these animations was generated by the same program that created the macroscopic pattern—it’s not an After Effects filter or anything that was added after the fact. The program is written in JavaScript with p5.js, Node.js, and Socket.io, and the rendering of the animation frames was made with Puppeteer (the “new Headless Chrome”) and ffmpeg.
The whole program can be found on GitHub and is released freely under a Gnu Gpl 3.0 Licence. This web page (including text and images, except for the logo of the Conseil des Arts et des Lettres du Québec used at the bottom of the page) is released under a Free Art Licence 1.3.
Sources
I first learned about diffusion limited aggregation from a video tutorial created by Daniel Shiffman and presented on his YouTube channel The Coding Train.
Thanks
I thank the Gouvernement du Québec for the financial support granted to this project in virtue of measure 62 of the Plan culturel numérique du Québec administered by the Conseil des arts et des lettres du Québec.


Remaking Education: Design
Perfect typography depends on perfect harmony between all of its elements. Harmony is determined by relationships or proportions. Proportions are hidden everywhere. words themselves.
Perfect typography depends on perfect harmony between all of its elements. Harmony is determined by relationships or proportions. Proportions are hidden everywhere. words themselves.


@ExperimentalCoroutinesApi @ObsoleteCoroutinesApi fun khomeApplication(init: KhomeBuilder = {}): KhomeApplication
The main entry point to start your application
init
- The type safe builder function to access the receiver
Return
KhomeApplication


Paused resources will not be reconciled by a controller. By resuming a resource, we allow it to be reconciled again. Currently only deployments support being resumed.
Examples:
# Resume an already paused deployment
kubectl rollout resume deployment/nginx
kubectl rollout resume RESOURCE [options]
Use "kubectl options" for a list of global command-line options (applies to all commands).


Everyone can see all information about this vote.
{% elif question.display_pref == 2 %}Only names of voters will be shown.
{% elif question.display_pref == 3 %}Only numbers of voters will be shown.
{% elif question.display_pref == 5 %}All votes will be shown, but usernames will be hidden.
{% else %}You can only see your own vote.
{% endif %}| {{ user.username }} | {{ user.email }} |
There are a total of {{question.question_voters.count}} unique voters.
{% else %}| {{ request.user.username }} | {{ request.user.email }} |


Filtered By
All Facilities
Filtered From
12th Nov, 2016.
Filtered To
12th Nov, 2016.
2,922,000
Patients
Detail
₦
₦500,322,000
Pay In
Detail
₦
₦200,022,000
Pay Outs
Detail
₦
₦300,422,000
Profit Facilities
Detail
300,422,000
Appointments
Detail
300,422,000
Check Ins
Detail
300,422,000
Sucessful Transactions
Detail
300,422,000
Logged In Users
Detail


×
About
The Sick-Slider is a website to implement different slick carousel styles. The UI of this website is designed by me. The Theme of this website is "Sliding".
This website is Designed and Created by MANAV KAPILA and is licensed under MIT License.


React Js Projesi nasil github pages ile host edilebilir?
Hellö. Bu yazida basima gelen bir olayi not etmeyi hedefliyorum. Baslik bu konu icin gayet aciklayici.
Read MoreMany software techs, comics, jokes, gis operations, brainstorming smiling activities.
Actually, more. I never forget smiling and be happy. I am doing my dream job. Learning new things makes me feel like at the top of everest. Maybe at the coffe shop at Amsterdam :)
If you want to talk with me, stay in touch. I always check my mails.
| Name | Atakan Savas |
| Date of birth | September 23, 1993 |
|<EMAIL_ADDRESS>| |
| Address | Istanbul | Turkey |
| Skype |<EMAIL_ADDRESS>|
If a man is called to be a street sweeper, he should sweep streets even as a Michaelangelo painted, or Beethoven composed music or Shakespeare wrote poetry. He should sweep streets so well that all the hosts of heaven and earth will pause to say, 'Here lived a great street sweeper who did his job well.'
| Name | Anadolu Universty |
| Address | Distance Education |
| Period | 2017-Current |
| Level | Management Informatin Systems |
In it ;
Web design, data structures systems, programming, network systems.
Management ;
Management and organizations, business finance
| Name | Sakarya Universty |
| Address | Distance Education |
| Period | 2014-2014 |
| Level | Computer Programming |
Algorithm, english, data management systems, system analysis. I was also working while going to school. Hard times :)
| Name | Umraniye Anatolian School |
| Address | Istanbul |
| Period | 2010-2014 |
| Level | High School - Computer Programming |
Algorithm, english and programming lessons. I started programming in this school.
| Company Name | KariyerNet |
| Address | Istanbul |
| Period | 2018 June-Current |
| Post | Back End Developer |
Turkey's biggest employement platform.
Microservice architecture ,Scrum, Agile ,Net core ,CI / CD, Performance codding, pair programming, Unit Tests...
| Company Name | Imarsorgulama.com |
| Address | Istanbul |
| Period | September 2016 - June 2018 |
| Post | Full Stack Developer |
This project can detect illegal construction. (B-B / B-C) Calculate buildings. Result is in 3d mode.
OOP, MVC, Soap, WCF, Geoserver, PostgreSql, Typescript.
| Company Name | Creaup Studio |
| Address | Istanbul |
| Period | May 2016 - September 2016 |
| Post | Full Stack Developer |
My own startup. (Fith friends)
c#.net, Php Symphony, Apache Cordova, Javascript.
| Company Name | Avmeda |
| Address | Istanbul |
| Period | September 2015 - May 2016 |
| Post | Full Stack Developer |
International software development company serving broadcast solutions.
Server based applications (TCP-IP), Signalr, WPF, Windows Services.
| Company Name | AloBiletHatti.com |
| Address | Istanbul |
| Period | April 2014 - September 2015 |
| Post | Full Stack Developer |
Fly ticket web site. Users can buy fly tickets. (B-B / B-C)
.Net, MVC, Mssql, Kanban,
Hellö. Bu yazida basima gelen bir olayi not etmeyi hedefliyorum. Baslik bu konu icin gayet aciklayici.
Read MoreHi all. There is another story. In this story, i will try to connect google maps to postgresql with asp.net mvc project.
Read More


Browse Thousands of Docs for Web Developers
And even more resources for: Mobile Web Apps · Firefox Add-ons · Mozilla Applications
Latest News & Updates
-
Mozilla Hacks Weekly, November 10th 2011
We do like reading in Mozilla’s Developer Engagement Team – here are our latest recommendations for you! Weekly links November 10th 2011 If there is anything you think we should read or know about, don’t hesitate to post a comment, contact us on Twitter or through any other mean. The ...
-
Naoki Hirata: Mobile Newsletter – Week of November 11th 2011
Welcome Firefox Mobile testers! Our goal is to provide you with mobile news and guidance towards how and where you as a tester can help out! This Week’s Headlines! Newsletter has now changed to a weekly updates on the Native UI Firefox Mobile Test day is tomorrow! It’s a great ...
-
SDK Hack day: what to expect
In just over a week the Jetpack project will be hosting an SDK hack day in Mountain View. I’ve decided to keep the event’s format as flexible as possible so as to make sure we can accommodate various levels of experience: If you’re a web developer curious about branching out ...
-
Firefox Update, Popcorn, Finding Mozillians and more…
about:mozilla is a weekly round-up of news and contribution opportunities. Here’s what’s happening this week. Firefox Update An update to Firefox for Windows, Mac, Linux and Android has been released and includes new features that make Web browsing easier, including Twitter search, a clean up of add-ons installed by third ...


By default, the inspection considers a compile-time constant a format string if it's used as an argument to the corresponding methods on
java.util.Formatter
, java.lang.String
, java.io.PrintWriter
or java.io.PrintStream
.
Example:
String.format("x = %d, y = %d", 42);
Use the inspection settings to mark additional classes and methods as related to string formatting.
As an alternative, you can use the org.intellij.lang.annotations.PrintFormat
annotation
to mark the format string method parameter. In this case,
the format arguments parameter must immediately follow the format string and be the last method parameter. Example:
void myFormatMethod(int mode, @PrintFormat String formatString, Object... args) {...}
Methods annotated in this way will also be recognized by this inspection.


|
138. Games of Chess Time Limit: 0.5 sec, Memory Limit: 1 MB N friends gathered in order to play chess, according to the following rules. In the first game, two of the N friends will play. In the second game, the winner of the first game will play against another friend (maybe even the same friend who lost the first game). In the third game, the winner of the second game will play against someone else and so on.. No game will end as a draw (tie). Given the number of games each of the N friends played, find a schedule for the games, so that the above rules are obeyed. Input The first line contains the number of friends N (2<=N<=100). The second line contains N integers, separated by blanks, representing the number of games each friend played. The first number represents the number of games played by the first friend, the second number represents the number of games played by the second friend and so on.. Output The first line should contain the number of games played
by all the friends (it will be an integer between 1 and 10
000, for every test case). Let's suppose this number is G.
Then, G lines follow, each of them containing two integers,
describing the games. The first line contains the numbers of the two
friends who played the first game. The friend printed first is considered
to be the winner. Each of the next G-1 lines contain the integers
a and b, where a<>b and a or b is
the winner of the previous game. The friend printed first on the line is
considered to be the winner of the game. Sample Input 4 2 4 1 5 Sample Output 6 4 3 4 1 2 4 2 1 4 2 2 4 | ||||||
|


SUBROUTINE DGGSVD( JOBU, JOBV, JOBQ, M, N, P, K, L, A, LDA, B, $ LDB, ALPHA, BETA, U, LDU, V, LDV, Q, LDQ, WORK, $ IWORK, INFO ) * * -- LAPACK driver routine (version 3.1) -- * Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd.. * November 2006 * * .. Scalar Arguments .. CHARACTER JOBQ, JOBU, JOBV INTEGER INFO, K, L, LDA, LDB, LDQ, LDU, LDV, M, N, P * .. * .. Array Arguments .. INTEGER IWORK( * ) DOUBLE PRECISION A( LDA, * ), ALPHA( * ), B( LDB, * ), $ BETA( * ), Q( LDQ, * ), U( LDU, * ), $ V( LDV, * ), WORK( * ) * .. * * Purpose * ======= * * DGGSVD computes the generalized singular value decomposition (GSVD) * of an M-by-N real matrix A and P-by-N real matrix B: * * U'*A*Q = D1*( 0 R ), V'*B*Q = D2*( 0 R ) * * where U, V and Q are orthogonal matrices, and Z' is the transpose * of Z. Let K+L = the effective numerical rank of the matrix (A',B')', * then R is a K+L-by-K+L nonsingular upper triangular matrix, D1 and * D2 are M-by-(K+L) and P-by-(K+L) "diagonal" matrices and of the * following structures, respectively: * * If M-K-L >= 0, * * K L * D1 = K ( I 0 ) * L ( 0 C ) * M-K-L ( 0 0 ) * * K L * D2 = L ( 0 S ) * P-L ( 0 0 ) * * N-K-L K L * ( 0 R ) = K ( 0 R11 R12 ) * L ( 0 0 R22 ) * * where * * C = diag( ALPHA(K+1), ... , ALPHA(K+L) ), * S = diag( BETA(K+1), ... , BETA(K+L) ), * C**2 + S**2 = I. * * R is stored in A(1:K+L,N-K-L+1:N) on exit. * * If M-K-L < 0, * * K M-K K+L-M * D1 = K ( I 0 0 ) * M-K ( 0 C 0 ) * * K M-K K+L-M * D2 = M-K ( 0 S 0 ) * K+L-M ( 0 0 I ) * P-L ( 0 0 0 ) * * N-K-L K M-K K+L-M * ( 0 R ) = K ( 0 R11 R12 R13 ) * M-K ( 0 0 R22 R23 ) * K+L-M ( 0 0 0 R33 ) * * where * * C = diag( ALPHA(K+1), ... , ALPHA(M) ), * S = diag( BETA(K+1), ... , BETA(M) ), * C**2 + S**2 = I. * * (R11 R12 R13 ) is stored in A(1:M, N-K-L+1:N), and R33 is stored * ( 0 R22 R23 ) * in B(M-K+1:L,N+M-K-L+1:N) on exit. * * The routine computes C, S, R, and optionally the orthogonal * transformation matrices U, V and Q. * * In particular, if B is an N-by-N nonsingular matrix, then the GSVD of * A and B implicitly gives the SVD of A*inv(B): * A*inv(B) = U*(D1*inv(D2))*V'. * If ( A',B')' has orthonormal columns, then the GSVD of A and B is * also equal to the CS decomposition of A and B. Furthermore, the GSVD * can be used to derive the solution of the eigenvalue problem: * A'*A x = lambda* B'*B x. * In some literature, the GSVD of A and B is presented in the form * U'*A*X = ( 0 D1 ), V'*B*X = ( 0 D2 ) * where U and V are orthogonal and X is nonsingular, D1 and D2 are * ``diagonal''. The former GSVD form can be converted to the latter * form by taking the nonsingular matrix X as * * X = Q*( I 0 ) * ( 0 inv(R) ). * * Arguments * ========= * * JOBU (input) CHARACTER*1 * = 'U': Orthogonal matrix U is computed; * = 'N': U is not computed. * * JOBV (input) CHARACTER*1 * = 'V': Orthogonal matrix V is computed; * = 'N': V is not computed. * * JOBQ (input) CHARACTER*1 * = 'Q': Orthogonal matrix Q is computed; * = 'N': Q is not computed. * * M (input) INTEGER * The number of rows of the matrix A. M >= 0. * * N (input) INTEGER * The number of columns of the matrices A and B. N >= 0. * * P (input) INTEGER * The number of rows of the matrix B. P >= 0. * * K (output) INTEGER * L (output) INTEGER * On exit, K and L specify the dimension of the subblocks * described in the Purpose section. * K + L = effective numerical rank of (A',B')'. * * A (input/output) DOUBLE PRECISION array, dimension (LDA,N) * On entry, the M-by-N matrix A. * On exit, A contains the triangular matrix R, or part of R. * See Purpose for details. * * LDA (input) INTEGER * The leading dimension of the array A. LDA >= max(1,M). * * B (input/output) DOUBLE PRECISION array, dimension (LDB,N) * On entry, the P-by-N matrix B. * On exit, B contains the triangular matrix R if M-K-L < 0. * See Purpose for details. * * LDB (input) INTEGER * The leading dimension of the array B. LDB >= max(1,P). * * ALPHA (output) DOUBLE PRECISION array, dimension (N) * BETA (output) DOUBLE PRECISION array, dimension (N) * On exit, ALPHA and BETA contain the generalized singular * value pairs of A and B; * ALPHA(1:K) = 1, * BETA(1:K) = 0, * and if M-K-L >= 0, * ALPHA(K+1:K+L) = C, * BETA(K+1:K+L) = S, * or if M-K-L < 0, * ALPHA(K+1:M)=C, ALPHA(M+1:K+L)=0 * BETA(K+1:M) =S, BETA(M+1:K+L) =1 * and * ALPHA(K+L+1:N) = 0 * BETA(K+L+1:N) = 0 * * U (output) DOUBLE PRECISION array, dimension (LDU,M) * If JOBU = 'U', U contains the M-by-M orthogonal matrix U. * If JOBU = 'N', U is not referenced. * * LDU (input) INTEGER * The leading dimension of the array U. LDU >= max(1,M) if * JOBU = 'U'; LDU >= 1 otherwise. * * V (output) DOUBLE PRECISION array, dimension (LDV,P) * If JOBV = 'V', V contains the P-by-P orthogonal matrix V. * If JOBV = 'N', V is not referenced. * * LDV (input) INTEGER * The leading dimension of the array V. LDV >= max(1,P) if * JOBV = 'V'; LDV >= 1 otherwise. * * Q (output) DOUBLE PRECISION array, dimension (LDQ,N) * If JOBQ = 'Q', Q contains the N-by-N orthogonal matrix Q. * If JOBQ = 'N', Q is not referenced. * * LDQ (input) INTEGER * The leading dimension of the array Q. LDQ >= max(1,N) if * JOBQ = 'Q'; LDQ >= 1 otherwise. * * WORK (workspace) DOUBLE PRECISION array, * dimension (max(3*N,M,P)+N) * * IWORK (workspace/output) INTEGER array, dimension (N) * On exit, IWORK stores the sorting information. More * precisely, the following loop will sort ALPHA * for I = K+1, min(M,K+L) * swap ALPHA(I) and ALPHA(IWORK(I)) * endfor * such that ALPHA(1) >= ALPHA(2) >= ... >= ALPHA(N). * * INFO (output) INTEGER * = 0: successful exit * < 0: if INFO = -i, the i-th argument had an illegal value. * > 0: if INFO = 1, the Jacobi-type procedure failed to * converge. For further details, see subroutine DTGSJA. * * Internal Parameters * =================== * * TOLA DOUBLE PRECISION * TOLB DOUBLE PRECISION * TOLA and TOLB are the thresholds to determine the effective * rank of (A',B')'. Generally, they are set to * TOLA = MAX(M,N)*norm(A)*MAZHEPS, * TOLB = MAX(P,N)*norm(B)*MAZHEPS. * The size of TOLA and TOLB may affect the size of backward * errors of the decomposition. * * Further Details * =============== * * 2-96 Based on modifications by * Ming Gu and Huan Ren, Computer Science Division, University of * California at Berkeley, USA * * ===================================================================== * * .. Local Scalars .. LOGICAL WANTQ, WANTU, WANTV INTEGER I, IBND, ISUB, J, NCYCLE DOUBLE PRECISION ANORM, BNORM, SMAX, TEMP, TOLA, TOLB, ULP, UNFL * .. * .. External Functions .. LOGICAL LSAME DOUBLE PRECISION DLAMCH, DLANGE EXTERNAL LSAME, DLAMCH, DLANGE * .. * .. External Subroutines .. EXTERNAL DCOPY, DGGSVP, DTGSJA, XERBLA * .. * .. Intrinsic Functions .. INTRINSIC MAX, MIN * .. * .. Executable Statements .. * * Test the input parameters * WANTU = LSAME( JOBU, 'U' ) WANTV = LSAME( JOBV, 'V' ) WANTQ = LSAME( JOBQ, 'Q' ) * INFO = 0 IF( .NOT.( WANTU .OR. LSAME( JOBU, 'N' ) ) ) THEN INFO = -1 ELSE IF( .NOT.( WANTV .OR. LSAME( JOBV, 'N' ) ) ) THEN INFO = -2 ELSE IF( .NOT.( WANTQ .OR. LSAME( JOBQ, 'N' ) ) ) THEN INFO = -3 ELSE IF( M.LT.0 ) THEN INFO = -4 ELSE IF( N.LT.0 ) THEN INFO = -5 ELSE IF( P.LT.0 ) THEN INFO = -6 ELSE IF( LDA.LT.MAX( 1, M ) ) THEN INFO = -10 ELSE IF( LDB.LT.MAX( 1, P ) ) THEN INFO = -12 ELSE IF( LDU.LT.1 .OR. ( WANTU .AND. LDU.LT.M ) ) THEN INFO = -16 ELSE IF( LDV.LT.1 .OR. ( WANTV .AND. LDV.LT.P ) ) THEN INFO = -18 ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.N ) ) THEN INFO = -20 END IF IF( INFO.NE.0 ) THEN CALL XERBLA( 'DGGSVD', -INFO ) RETURN END IF * * Compute the Frobenius norm of matrices A and B * ANORM = DLANGE( '1', M, N, A, LDA, WORK ) BNORM = DLANGE( '1', P, N, B, LDB, WORK ) * * Get machine precision and set up threshold for determining * the effective numerical rank of the matrices A and B. * ULP = DLAMCH( 'Precision' ) UNFL = DLAMCH( 'Safe Minimum' ) TOLA = MAX( M, N )*MAX( ANORM, UNFL )*ULP TOLB = MAX( P, N )*MAX( BNORM, UNFL )*ULP * * Preprocessing * CALL DGGSVP( JOBU, JOBV, JOBQ, M, P, N, A, LDA, B, LDB, TOLA, $ TOLB, K, L, U, LDU, V, LDV, Q, LDQ, IWORK, WORK, $ WORK( N+1 ), INFO ) * * Compute the GSVD of two upper "triangular" matrices * CALL DTGSJA( JOBU, JOBV, JOBQ, M, P, N, K, L, A, LDA, B, LDB, $ TOLA, TOLB, ALPHA, BETA, U, LDU, V, LDV, Q, LDQ, $ WORK, NCYCLE, INFO ) * * Sort the singular values and store the pivot indices in IWORK * Copy ALPHA to WORK, then sort ALPHA in WORK * CALL DCOPY( N, ALPHA, 1, WORK, 1 ) IBND = MIN( L, M-K ) DO 20 I = 1, IBND * * Scan for largest ALPHA(K+I) * ISUB = I SMAX = WORK( K+I ) DO 10 J = I + 1, IBND TEMP = WORK( K+J ) IF( TEMP.GT.SMAX ) THEN ISUB = J SMAX = TEMP END IF 10 CONTINUE IF( ISUB.NE.I ) THEN WORK( K+ISUB ) = WORK( K+I ) WORK( K+I ) = SMAX IWORK( K+I ) = K + ISUB ELSE IWORK( K+I ) = K + I END IF 20 CONTINUE * RETURN * * End of DGGSVD * END


{{fileName}}
Parent folder: {{folderPath}}
Created on: {{dateCreated}}
Encoding: {{recordingInfo.encoding}}
Duration: {{displayDuration}}
File size: {{recordingInfo.size + 44}} bytes
Sample rate: {{recordingInfo.sampleRate}} Hz
# of samples: {{recordingInfo.nSamples}}


{{block.label}}
Label
Block Duration:
percent
hours
minutes
seconds
Block type
interstitial
block
Block Source
VO
ASSET_LIBRARY
Sort By
date
rank
description
media file
Show Filters
+ Add filter
filter name
includeFavoritesOnly
excludeFavorites
includeMP3Only
includeVideoOnly
excludeSources
includeSpotifyOnly
filter params
Delete
Source Block Mappings
+ Add Mapping
source
description
label
media
Delete
Move Up
Move Down
Delete
Show Duration:
hours
minutes
seconds
Add Block +
Save All


The Anchore Policy Hub is a centralized repository of resources that can be loaded into/consumed by any anchore engine installation. To learn about this site's resources, please visit Anchore Policy Hub on github.


Every website should be built with two primary goals: Firstly, it needs to work across all devices (Flixable). Secondly, it needs to be fast as possible (Fluency).
Every website should be built with two primary goals: Firstly, it needs to work across all devices (Flixable). Secondly, it needs to be fast as possible (Fluency).
Every website should be built with two primary goals: Firstly, it needs to work across all devices (Flixable). Secondly, it needs to be fast as possible (Fluency).
Let you have A Beautiful Website.
contact-meSadeq Ameen
Thats my first project in web desining please tell me if it was impressive
Have a good day


--- layout: default title: Events description: Past and upcoming Chi Hack Night presentations and events. We have hosted and recorded over 300 presentations since 2012. You can read about and watch them here. ---
Past and upcoming Chi Hack Night presentations and events. We have hosted and recorded over 300 presentations since 2012. You can read about and watch them here.
Have a talk you'd like to give at Chi Hack Night? Learn more about speaker submissions »
| Date | # | Event | Speaker(s) | Tags |
|---|---|---|---|---|
|
{{ post.date | date: "%b %-d, %Y" }} |
{{post.event_id}} | {{ post.title }} {% if post.youtube_id %} {% endif %} |
{% for speaker in post.speakers %}
{{speaker}} {% endfor %} |
{% for tag in post.tags %}
{{tag}} {% endfor %} |


This is a really simple demo of the superformula. To change the shape that is drawn, use the console to modify the six parameters: a, b, m, n1, n2, n3. To redraw the shape, execute the draw() function.
a, b, m, n1, n2, n3
draw()


This demo syncs the map center position with the URL, and vice versa, using the url-hash-center and url-hash-param property.


Full Stack Web Developer
32, Arambag, Motijheel
I like to solve problems, learn new technologies and can’t get my hands off new hardware tools. I like to integrate the best of both worlds. Implementing crazy, new and innovative project that comes right out of my head.


import _ from 'lodash';
import Sync from './sync';
import Helpers from './helpers';
import EagerRelation from './eager';
import Errors from './errors';
import CollectionBase from './base/collection';
import Promise from './base/promise';
import createError from 'create-error';
/**
* @class Collection
* @extends CollectionBase
* @inheritdoc
* @classdesc
*
* Collections are ordered sets of models returned from the database, from a
* {@link Model#fetchAll fetchAll} call. They may be used with a suite of
* {@link http://lodash.com/ Lodash} methods.
*
* @constructor
* @description
*
* When creating a {@link Collection}, you may choose to pass in the initial
* array of {@link Model models}. The collection's {@link Collection#comparator
* comparator} may be included as an option. Passing `false` as the comparator
* option will prevent sorting. If you define an {@link Collection#initialize
* initialize} function, it will be invoked when the collection is created.
*
* @example
* let tabs = new TabSet([tab1, tab2, tab3]);
*
* @param {(Model[])=} models Initial array of models.
* @param {Object=} options
* @param {bool} [options.comparator=false]
* {@link Collection#comparator Comparator} for collection, or `false` to disable sorting.
*/
let BookshelfCollection = CollectionBase.extend({
/**
* @method Collection#through
* @private
* @description
* Used to define passthrough relationships - `hasOne`, `hasMany`, `belongsTo`
* or `belongsToMany`, "through" an `Interim` model or collection.
*/
through: function(Interim, foreignKey, otherKey) {
return this.relatedData.through(this, Interim, {throughForeignKey: foreignKey, otherKey: otherKey});
},
/**
* @method Collection#fetch
* @description
* Fetch the default set of models for this collection from the database,
* resetting the collection when they arrive. If you wish to trigger an error
* if the fetched collection is empty, pass `{require: true}` as one of the
* options to the {@link Collection#fetch fetch} call. A {@link
* Collection#fetched "fetched"} event will be fired when records are
* successfully retrieved. If you need to constrain the query performed by
* `fetch`, you can call the {@link Collection#query query} method before
* calling `fetch`.
*
* *If you'd like to only fetch specific columns, you may specify a `columns`
* property in the options for the `fetch` call.*
*
* The `withRelated` option may be specified to fetch the models of the
* collection, eager loading any specified {@link Relation relations} named on
* the model. A single property, or an array of properties can be specified as
* a value for the `withRelated` property. The results of these relation
* queries will be loaded into a relations property on the respective models,
* may be retrieved with the {@link Model#related related} method.
*
* @fires Collection#fetched
* @throws {Collection.EmptyError}
* Upon a sucessful query resulting in no records returns. Only fired if `require: true` is passed as an option.
*
* @param {Object=} options
* @param {bool} [options.required=false] Trigger a {@link Collection.EmptyError} if no records are found.
* @param {string|string[]} [options.withRelated=[]] A relation, or list of relations, to be eager loaded as part of the `fetch` operation.
* @returns {Promise<Collection>}
*/
fetch: Promise.method(function(options) {
options = options ? _.clone(options) : {};
return this.sync(options)
.select()
.bind(this)
.tap(function(response) {
if (!response || response.length === 0) {
if (options.require) throw new this.constructor.EmptyError('EmptyResponse');
return Promise.reject(null);
}
})
// Now, load all of the data onto the collection as necessary.
.tap(this._handleResponse)
// If the "withRelated" is specified, we also need to eager load all of the
// data on the collection, as a side-effect, before we ultimately jump into the
// next step of the collection. Since the `columns` are only relevant to the current
// level, ensure those are omitted from the options.
.tap(function(response) {
if (options.withRelated) {
return this._handleEager(response, _.omit(options, 'columns'));
}
})
.tap(function(response) {
/**
* @event Collection#fetched
*
* @description
* Fired after a `fetch` operation. A promise may be returned from the
* event handler for async behaviour.
*
* @param {Collection} collection The collection performing the {@link Collection#fetch}.
* @param {Object} reponse Knex query response.
* @param {Object} options Options object passed to {@link Collection#fetch fetch}.
* @returns {Promise}
*/
return this.triggerThen('fetched', this, response, options);
})
.catch(function(err) {
if (err !== null) throw err;
this.reset([], {silent: true});
})
.return(this);
}),
/**
* @method Collection#count
* @since 0.8.2
* @description
*
* Get the number of records in the collection's table.
*
* @example
*
* // select count(*) from shareholders where company_id = 1 and share > 0.1;
* Company.forge(({id:1})
* .shareholders()
* .query('where', 'share', '>', '0.1')
* .count()
* .then(function(count) {
* assert(count === 3);
* });
*
* @param {string} [column='*']
* Specify a column to count - rows with null values in this column will be excluded.
* @param {Object=} options
* Hash of options.
* @returns {Promise<Number>}
* A promise resolving to the number of matching rows.
*/
count: Promise.method(function(column, options) {
if (!_.isString(column)) {
options = column;
column = undefined;
}
if (options) options = _.clone(options);
return this.sync(options).count(column)
}),
/**
* @method Collection#fetchOne
* @description
*
* Fetch and return a single {@link Model model} from the collection,
* maintaining any {@link Relation relation} data from the collection, and
* any {@link Collection#query query} parameters that have already been passed
* to the collection. Especially helpful on relations, where you would only
* like to return a single model from the associated collection.
*
* @example
*
* // select * from authors where site_id = 1 and id = 2 limit 1;
* new Site({id:1})
* .authors()
* .query({where: {id: 2}})
* .fetchOne()
* .then(function(model) {
* // ...
* });
*
* @param {Object=} options
* @param {boolean} [options.require=false]
* If `true`, will reject the returned response with a {@link
* Model.NotFoundError NotFoundError} if no result is found.
* @param {(string|string[])} [options.columns='*']
* Limit the number of columns fetched.
* @param {Transaction} options.transacting
* Optionally run the query in a transaction.
*
* @throws {Model.NotFoundError}
* @returns {Promise<Model|undefined>}
* A promise resolving to the fetched {@link Model model} or `undefined` if none exists.
*/
fetchOne: Promise.method(function(options) {
let model = new this.model();
model._knex = this.query().clone();
this.resetQuery();
if (this.relatedData) model.relatedData = this.relatedData;
return model.fetch(options);
}),
/**
* @method Collection#load
* @description
* `load` is used to eager load relations onto a Collection, in a similar way
* that the `withRelated` property works on {@link Collection#fetch fetch}.
* Nested eager loads can be specified by separating the nested relations with
* `'.'`.
*
* @param {string|string[]} relations The relation, or relations, to be loaded.
* @param {Object=} options Hash of options.
* @param {Transaction=} options.transacting
*
* @returns {Promise<Collection>} A promise resolving to this {@link
* Collection collection}
*/
load: Promise.method(function(relations, options) {
if (!_.isArray(relations)) relations = [relations]
options = _.extend({}, options, {shallow: true, withRelated: relations});
return new EagerRelation(this.models, this.toJSON(options), new this.model())
.fetch(options)
.return(this);
}),
/**
* @method Collection#create
* @description
*
* Convenience to create a new instance of a {@link Model model} within a
* collection. Equivalent to instantiating a model with a hash of {@link
* Model#attributes attributes}, {@link Model#save saving} the model to the
* database, and adding the model to the collection after being successfully
* created.
*
* @param {Object} model A set of attributes to be set on the new model.
* @param {Object=} options
* @param {Transaction=} options.transacting
*
* @returns {Promise<Model>} A promise resolving with the new {@link Modle
* model}.
*/
create: Promise.method(function(model, options) {
options = options ? _.clone(options) : {};
let relatedData = this.relatedData;
model = this._prepareModel(model, options);
// If we've already added things on the query chain,
// these are likely intended for the model.
if (this._knex) {
model._knex = this._knex;
this.resetQuery();
}
return Helpers
.saveConstraints(model, relatedData)
.save(null, options)
.bind(this)
.then(function() {
if (relatedData && relatedData.type === 'belongsToMany') {
return this.attach(model, _.omit(options, 'query'));
}
})
.then(function() { this.add(model, options); })
.return(model);
}),
/**
* @method Collection#resetQuery
* @description
* Used to reset the internal state of the current query builder instance.
* This method is called internally each time a database action is completed
* by {@link Sync}.
*
* @returns {Collection} Self, this method is chainable.
*/
resetQuery: function() {
this._knex = null;
return this;
},
/**
* @method Collection#query
* @description
*
* `query` is used to tap into the underlying Knex query builder instance for
* the current collection. If called with no arguments, it will return the
* query builder directly. Otherwise, it will call the specified `method` on
* the query builder, applying any additional arguments from the
* `collection.query` call. If the `method` argument is a function, it will be
* called with the Knex query builder as the context and the first argument.
*
* @example
*
* let qb = collection.query();
* qb.where({id: 1}).select().then(function(resp) {...
*
* collection.query(function(qb) {
* qb.where('id', '>', 5).andWhere('first_name', '=', 'Test');
* }).fetch()
* .then(function(collection) {...
*
* collection
* .query('where', 'other_id', '=', '5')
* .fetch()
* .then(function(collection) {
* ...
* });
*
* @param {function|Object|...string=} arguments The query method.
* @returns {Collection|QueryBuilder}
* Will return this model or, if called with no arguments, the underlying query builder.
*
* @see {@link http://knexjs.org/#Builder Knex `QueryBuilder`}
*/
query: function() {
return Helpers.query(this, _.toArray(arguments));
},
/**
* @method Collection#query
* @private
* @description Creates and returns a new `Bookshelf.Sync` instance.
*/
sync: function(options) {
return new Sync(this, options);
},
/**
* @method Collection#_handleResponse
* @private
* @description
* Handles the response data for the collection, returning from the
* collection's `fetch` call.
*/
_handleResponse: function(response) {
let relatedData = this.relatedData;
this.set(response, {silent: true, parse: true}).invoke('_reset');
if (relatedData && relatedData.isJoined()) {
relatedData.parsePivot(this.models);
}
},
/**
* @method Collection#_handleEager
* @private
* @description
* Handle the related data loading on the collection.
*/
_handleEager: function(response, options) {
return new EagerRelation(this.models, response, new this.model()).fetch(options);
}
}, {
extended: function(child) {
/**
* @class Collection.NotFoundError
* @description
* Thrown when no records are found by {@link Collection#fetch fetch},
* when called with the `{require: true}` option.
*/
child.EmptyError = createError(this.EmptyError)
}
});
BookshelfCollection.EmptyError = Errors.EmptyError
export default BookshelfCollection;


Give us an option to disable Amazon lookups!!
-
anonymous
I hate to go against what seems to be the mainstream flow here, but as a registered user I ask that you give us an option to disable amazon cover looks, yet still show the cover album art we already have stored. I have a G4 550 powerbook, which should be plenty of computing power for this application, yet when Synergy is running I have noticeable slowdown on my machine while it calls lookupd, etc. Frankly, I don't think Synergy's method of cover art lookup is the most optimized - I use Clutter for my album art downloads and it works a lot better. Basically, I don't want Synergy doing all kinds of crap in the background - I download and paid for it because it was a lightweight iTunes controller and song display. Please give us an option to turn this feature off but still retain album art display in future version!
-
Greg Hurrell
This kind of option should be easy to add.
In the meantime, if you just make sure your art is in iTunes, then Synergy will never look on Amazon for it...
-
anonymous
Just a note - I'm also on a 550MHz PBG4 but I have no problems with slowdowns when Synergy performs artwork lookups. I don't know what would be causing our two systems to perform differently, but I'm pretty sensitive to performance-taxing programs (one reason I wish Apple would provide another way of getting iTunes status so Synergy wouldn't have to poll) so I don't think I'm not noticing it.
-
anonymous
Wincent, I have all of my art in iTunes, but sometimes Synergy decides to download it from Amazon anyways. It doesn't slow down my system, but it does mean that when the floater pops up the art usually hasn't been downloaded yet, whereas when it uses the local artwork, it's there instantly. It's a bit annoying, and I second the request for a "Show local artwork only" option.
-
Greg Hurrell
It would be useful if you could reproduce this fault (ie. identify what kind of song it happens on). To do so you would delete the copy of the downloaded art (choose "Show album covers folder" from the Synergy Global Menu) and the next time you run Synergy and play that song, see what it does.
I can assure you that Synergy always asks iTunes for art first, so if iTunes is not giving it for a particular song, we need to work out why.
-
anonymous
I'd also like this option, though for a different reason. I use FetchArt to make sure iTunes has album art for my music but some tracks and albums don't have any yet. I'd rather Synergy didn't download art as it will most likely be duplicated at some point or another in iTunes and I'd rather Synergy pull the art from iTunes, if it has it. Turning it off would be a great option.
Reply
This topic is now closed.


Menu
First Tending
Second Tending
Third Tending
Hatching Day
▼
Continue to next event.
Wait till the GM tell you.
Continue to next event.
Wait till the GM tell you.
Continue to next event.
Wait till the GM tell you.
Story End, Hatching Day...


| LOD | 5 |
|---|---|
| FPS | 0 |
| WebGPU Status | 😰 ... |
This is a hybrid of ray casting/marching (with scalar field gradients instead of a signed distance field) and marching cubes (minus the polygonization). Maybe there is a proper name for it in the graphics circles?
I am using a compute shader to create a 3D texture with scalar field values and gradients, and sampling it in the fragment shader (the thing that shoots it with ray 🙂)
| R | Binds mouse dragging to model rotation | |
| C | Binds mouse dragging to contour value | |
| M | Binds mouse dragging to noise matrix | |
| S | Binds mouse dragging to noise scaling factor | |
| ⬆ | Increase level of detail | |
| ⬇ | Decrease level of detail |