Emotional intelligence is made up of a number of components. Firstly, emotional intelligence refers to a person’s self-awareness and level of consciousness relating to their own inner state. To have a high level of EQ in this regard means to be connected to one’s own emotions and inner thought life. A person who is not developed in this regard will be highly reactive, mechanical, and unaware of how their own mental and emotional state is influencing their behaviors and interactions with others. Low self-awareness and consciousness will result in a person becoming “possessed” by a feeling that arises unconsciously, reacting to stimuli immediately without consideration. In contrast, a person who has high levels of self-aware consciousness will observe these responsive feeling arises, access them from a place of meta-awareness without judgement, and respond consciously with careful consideration, choosing their words and behavior from a place of calm thoughtfulness. Stemming from this place of meta-awareness and high consciousness, an emotionally intelligent person will also be better equipped to read another person’s feelings and pick up on subtle nonverbal ques. They will have a more developed ability to access another’s emotional state, body language, motivations, and unspoken subtext. They will be more in tune with the energy, or “vibe” in a social setting, reading social ques and more nuanced indicators that suggest what an appropriate response may be. Emotionally intelligent persons are high in empathy and find it easy to connect with others and form social bonds. They are less neurotic, self-absorbed, and concerned with how they appear. Instead, they are able to be present with another person, listen intently, and respond from a place of non-judgmental awareness.
How is it different to IQ?
IQ is a way of accessing a person’s fluid-intelligence and baseline cognitive ability. It gives no indication of a person’s ability to relate, communicate with interpersonal savvy, or empathise. As such, a person with high IQ but low EQ may be difficult to work with if they cannot use their intelligence in a social setting (e.g. a company or team project).
Why is it important?
Emotional intelligence is crucial to working in teams, or companies. The ability to read a room, interpret unspoken social ques, empathise with collogues, and communicate with members of a team is essential. Having skills and knowledge is of little use if it cannot be applied in the context of a team project, or even a free-lance engineer who needs to communicate and form trusting social bonds with their client. Interpersonal soft-skills are needed to win business, make sales, work effectively in teams, and present results back to seniors.
A have a positive bias towards mindfullness going into this section of the course. Over the past few years it has been of personal interest to me, leading me to read books, watch YouTube videos, and engage with mindfullness apps. I strongly believe in mindfullness as a meta-tool for life, to improve self-awareness and EQ, hapiness, focus, mental clarity, and moment to moment peace.
Enjoyable. Mindfullness practices allow me to step out of day to day experience and reset. Mindfullness practice also usually will give me some indications of things I need to improve, fix, or actions I need to take to have peace. If I sit to meditate for 10 minutes usually the first 5 are spent ruminating on things I need to do, or problems I need to solve. I treat this as a "to-do" list from my deeper intelligence.
Illustration by JR Bee, Verywell
I am commited to spending 15 minutes in mindfullness mediation every morning before beginning my course work. This is a practice I already have in my life (although I am not always consistent). My commitment therefore, is to make it an offical set intention. I will aim not to miss days.
My expereince of listening and looping was very postive. It felt good to have the space to share freely and openly while being heard. Speaking my thoughts aloud to another person gave me an opportunity to clarify how I was feeling and perception of my own experiences. Benjamin was a great listener and I really felt a postitive, supporting connection to my cohort classate. Although I have many supportive people in my life who I can speak with about the things I am going through, having a designated time and space to really be open and focussed in my sharing was more profound and theraputic than what a standard conversation tends to be without the set intention.
I enjoyed the expeirence of listening fully to Benjamin share about his week. I had a sense of empathy and compassion towards him as I could easily relate to the underlying feelings he was expressing. A sense of connection and presence allowed me to feel less alone in my stresses and concerns with moving through foundations. I noticed how it felt good to be an open space for Benjamin to safely and freely voice his thoughts and emotions without fear of interuption or lack of interest. Many converstions unfortunately can feel like the other person is not truly listening and just waiting for an opportunity to chip back in with what is on their mind, so this intentional space of focus on the other person was a pleasant difference.
Back to index


Authenticator
Some Issuer 2
foo2
☰
73 69 97 1
＋
Cancel
Add Token
Done
Account Name
Issuer
Secret Key
Advanced Options
Time Based
Counter Based
6 Digits
7 Digits
8 Digits
SHA-1
SHA-256
SHA-512
Back
Info
Export Backup
Choose a password to export an encrypted backup of your token secrets.
Backup Password
Export Backup


Toggle navigation
DANE Doctor
About
The DANE Doctor is in!
Check out
these
examples!
Your results:
Usage
Selector
Matching type
Matches server certificate


{% extends "base.html" %} {% block title %}Settings – My IoT{% endblock %} {% block body %}
This section displays the currently running configuration. To change a setting, edit the configuration file and restart My IoT.
It's better if you use a version control system to store your configuration


percentage-based position:fixed
viewport-unit position:fixed
percentage-based position:absolute
viewport-unit position:absolute
This page has a small polyfill that makes ICB sizing behave like it used to.
OnResize handler calls will be displayed below with window.innerWidth and documentElement.clientHeight


Because Singapore's emissions are so much less than those of the United States, the graph shows them to be essentially 0 - which is not the case. We don't see anything of the pattern of how Singaporean emissions have changed over the past 60 years because the US emissions are so much larger. To show these two data sets together, it is better to graph them each individually.
in-context


EBD - Easton Bible DIctionary
Karkor
KARKOR
"KARKOR "foundation, a place in the open desert wastes on the east of Jordan (
Judges 8:10
), not far beyond Succoth and Penuel, to the south.
Here Gideon overtook and routed a fugitive band of Midianites under Zeba and Zalmunna, whom he took captive.
"KARKOR "foundation, a place in the open desert wastes on the east of Jordan (Judges 8:10), not far beyond Succoth and Penuel, to the south.
Here Gideon overtook and routed a fugitive band of Midianites under Zeba and Zalmunna, whom he took captive.


Jeopardy Game - TSMIT Biannual 2018
Topic 1
Topic 2
Topic 3
Topic 4
Topic 5
Topic 6
Topic 7
Loading ...


Check us out on Facebook
Share This page and like my facebook! Thanks!
These are older pics, newer ones to come asap.
Return to main page


Class ServiceCollectionAbstractionsExtensions
Provides useful IServiceCollection extensions for testing purposes.
Inheritance
Namespace:MyTested.AspNetCore.Mvc
Assembly:MyTested.AspNetCore.Mvc.Abstractions.dll
Syntax
public static class ServiceCollectionAbstractionsExtensions
Methods
| Improve this Doc View SourceAddCoreTesting(IServiceCollection)
Adds core MVC testing services.
Declaration
public static IServiceCollection AddCoreTesting(this IServiceCollection serviceCollection)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Remove(IServiceCollection, Type)
Removes а service from the IServiceCollection.
Declaration
public static IServiceCollection Remove(this IServiceCollection serviceCollection, Type service)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Remove(IServiceCollection, Type, Type)
Removes a service from the IServiceCollection.
Declaration
public static IServiceCollection Remove(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
| System.Type | implementationType | Service implementation type which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Remove<TService>(IServiceCollection)
Removes a service from the IServiceCollection.
Declaration
public static IServiceCollection Remove<TService>(this IServiceCollection serviceCollection)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
Remove<TService, TImplementation>(IServiceCollection)
Removes a service from the IServiceCollection.
Declaration
public static IServiceCollection Remove<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
| TImplementation | Service implementation type which will be removed. |
RemoveScoped(IServiceCollection, Type)
Removes a scoped service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveScoped(this IServiceCollection serviceCollection, Type service)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
RemoveScoped(IServiceCollection, Type, Type)
Removes a scoped service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveScoped(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
| System.Type | implementationType | Service implementation type which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
RemoveScoped<TService>(IServiceCollection)
Removes a scoped service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveScoped<TService>(this IServiceCollection serviceCollection)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
RemoveScoped<TService, TImplementation>(IServiceCollection)
Removes a scoped service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveScoped<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
| TImplementation | Service implementation type which will be removed. |
RemoveSingleton(IServiceCollection, Type)
Removes a singleton service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveSingleton(this IServiceCollection serviceCollection, Type service)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
RemoveSingleton(IServiceCollection, Type, Type)
Removes a singleton service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveSingleton(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
| System.Type | implementationType | Service implementation type which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
RemoveSingleton<TService>(IServiceCollection)
Removes a singleton service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveSingleton<TService>(this IServiceCollection serviceCollection)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
RemoveSingleton<TService, TImplementation>(IServiceCollection)
Removes a singleton service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveSingleton<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
| TImplementation | Service implementation type which will be removed. |
RemoveTransient(IServiceCollection, Type)
Removes a transient service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveTransient(this IServiceCollection serviceCollection, Type service)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
RemoveTransient(IServiceCollection, Type, Type)
Removes a transient service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveTransient(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be removed. |
| System.Type | implementationType | Service implementation type which will be removed. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
RemoveTransient<TService>(IServiceCollection)
Removes a transient service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveTransient<TService>(this IServiceCollection serviceCollection)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
RemoveTransient<TService, TImplementation>(IServiceCollection)
Removes a transient service from the IServiceCollection.
Declaration
public static IServiceCollection RemoveTransient<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be removed. |
| TImplementation | Service implementation type which will be removed. |
Replace(IServiceCollection, Type, Func<IServiceProvider, Object>, ServiceLifetime)
Replaces a service in the IServiceCollection.
Declaration
public static IServiceCollection Replace(this IServiceCollection serviceCollection, Type service, Func<IServiceProvider, object> implementationFactory, ServiceLifetime lifetime)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
| Microsoft.Extensions.DependencyInjection.ServiceLifetime | lifetime | The ServiceLifetime which will be applied on the replaced service. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Replace(IServiceCollection, Type, Type, ServiceLifetime)
Replaces a service in the IServiceCollection.
Declaration
public static IServiceCollection Replace(this IServiceCollection serviceCollection, Type service, Type implementationType, ServiceLifetime lifetime)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Type | implementationType | Service implementation type which will be used for replacement. |
| Microsoft.Extensions.DependencyInjection.ServiceLifetime | lifetime | The ServiceLifetime which will be applied on the replaced service. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Replace<TService>(IServiceCollection, Func<IServiceProvider, Object>, ServiceLifetime)
Replaces a service in the IServiceCollection.
Declaration
public static IServiceCollection Replace<TService>(this IServiceCollection serviceCollection, Func<IServiceProvider, object> implementationFactory, ServiceLifetime lifetime)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
| Microsoft.Extensions.DependencyInjection.ServiceLifetime | lifetime | The ServiceLifetime which will be applied on the replaced service. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
Replace<TService, TImplementation>(IServiceCollection, ServiceLifetime)
Replaces a service in the IServiceCollection.
Declaration
public static IServiceCollection Replace<TService, TImplementation>(this IServiceCollection serviceCollection, ServiceLifetime lifetime)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| Microsoft.Extensions.DependencyInjection.ServiceLifetime | lifetime | The ServiceLifetime which will be applied on the replaced service. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
| TImplementation | Service implementation type which will be used for replacement. |
ReplaceEnumerable(IServiceCollection, ServiceDescriptor)
Replaces multiple services in the IServiceCollection.
Declaration
public static void ReplaceEnumerable(this IServiceCollection serviceCollection, ServiceDescriptor descriptor)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| Microsoft.Extensions.DependencyInjection.ServiceDescriptor | descriptor | ServiceDescriptor providing the services. |
ReplaceEnumerable(IServiceCollection, IEnumerable<ServiceDescriptor>)
Replaces multiple services in the IServiceCollection.
Declaration
public static void ReplaceEnumerable(this IServiceCollection serviceCollection, IEnumerable<ServiceDescriptor> descriptors)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Collections.Generic.IEnumerable<Microsoft.Extensions.DependencyInjection.ServiceDescriptor> | descriptors | ServiceDescriptor providing the services. |
ReplaceLifetime(IServiceCollection, Type, ServiceLifetime)
Replaces service lifetime in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceLifetime(this IServiceCollection serviceCollection, Type service, ServiceLifetime lifetime)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| Microsoft.Extensions.DependencyInjection.ServiceLifetime | lifetime | The ServiceLifetime which will be applied on the replaced service. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceLifetime<TService>(IServiceCollection, ServiceLifetime)
Replaces service lifetime in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceLifetime<TService>(this IServiceCollection serviceCollection, ServiceLifetime lifetime)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| Microsoft.Extensions.DependencyInjection.ServiceLifetime | lifetime | The ServiceLifetime which will be applied on the replaced service. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
ReplaceScoped(IServiceCollection, Type, Func<IServiceProvider, Object>)
Replaces a scoped service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceScoped(this IServiceCollection serviceCollection, Type service, Func<IServiceProvider, object> implementationFactory)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceScoped(IServiceCollection, Type, Type)
Replaces a scoped service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceScoped(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Type | implementationType | Service implementation type which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceScoped<TService>(IServiceCollection, Func<IServiceProvider, Object>)
Replaces a scoped service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceScoped<TService>(this IServiceCollection serviceCollection, Func<IServiceProvider, object> implementationFactory)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
ReplaceScoped<TService, TImplementation>(IServiceCollection)
Replaces a scoped service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceScoped<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
| TImplementation | Service implementation type which will be used for replacement. |
ReplaceSingleton(IServiceCollection, Type, Func<IServiceProvider, Object>)
Replaces a singleton service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceSingleton(this IServiceCollection serviceCollection, Type service, Func<IServiceProvider, object> implementationFactory)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceSingleton(IServiceCollection, Type, Object)
Replaces a singleton service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceSingleton(this IServiceCollection serviceCollection, Type service, object implementationInstance)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Object | implementationInstance | Service implementation instance which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceSingleton(IServiceCollection, Type, Type)
Replaces a singleton service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceSingleton(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Type | implementationType | Service implementation type which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceSingleton<TService>(IServiceCollection, Func<IServiceProvider, Object>)
Replaces a singleton service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceSingleton<TService>(this IServiceCollection serviceCollection, Func<IServiceProvider, object> implementationFactory)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
ReplaceSingleton<TService>(IServiceCollection, Object)
Replaces a singleton service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceSingleton<TService>(this IServiceCollection serviceCollection, object implementationInstance)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Object | implementationInstance | Service implementation instance which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
ReplaceSingleton<TService, TImplementation>(IServiceCollection)
Replaces a singleton service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceSingleton<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
| TImplementation | Service implementation type which will be used for replacement. |
ReplaceTransient(IServiceCollection, Type, Func<IServiceProvider, Object>)
Replaces a transient service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceTransient(this IServiceCollection serviceCollection, Type service, Func<IServiceProvider, object> implementationFactory)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceTransient(IServiceCollection, Type, Type)
Replaces a transient service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceTransient(this IServiceCollection serviceCollection, Type service, Type implementationType)
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Type | service | Type of the service which will be replaced. |
| System.Type | implementationType | Service implementation type which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
ReplaceTransient<TService>(IServiceCollection, Func<IServiceProvider, Object>)
Replaces a transient service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceTransient<TService>(this IServiceCollection serviceCollection, Func<IServiceProvider, object> implementationFactory)where TService : class
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
| System.Func<System.IServiceProvider, System.Object> | implementationFactory | Service implementation factory which will be used for replacement. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
ReplaceTransient<TService, TImplementation>(IServiceCollection)
Replaces a transient service in the IServiceCollection.
Declaration
public static IServiceCollection ReplaceTransient<TService, TImplementation>(this IServiceCollection serviceCollection)where TService : class where TImplementation : class, TService
Parameters
| Type | Name | Description |
|---|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | serviceCollection | Instance of IServiceCollection type. |
Returns
| Type | Description |
|---|---|
| Microsoft.Extensions.DependencyInjection.IServiceCollection | The same IServiceCollection. |
Type Parameters
| Name | Description |
|---|---|
| TService | Type of the service which will be replaced. |
| TImplementation | Service implementation type which will be used for replacement. |


{% extends "standardLayout.html" %} {% block content %}
If you have problems using this site please contact the project manager Chris Greengrass on 0116 204 4771/4738/4768 or cg166@le.ac.uk


Linux L2 Admin and Devops Engineer
Value Labs, Hyderabad
Client: Snapfish
Team : Snapfish Site Reliability
Engineering Team
- Responsible for maintaining and improving our uptime
record and performance, monitoring network health, handling both planned and unplanned events.
-
- Installation/Upgrade Configuration of Servers.
-
- Deploying Patches and packages to production servers.
-
- User Administration on Linux servers.
-
- Verifying system logs, errors & warnings or hardware
failure errors and clean up old log files.
-
- Monitoring and performance tuning on Apache Tomcat
Servers.
-
- Managing File Systems and Server Performance.
-
- Performance Management- performance tickets high CPU
usage, memory usage and swap.
-
- Monitoring production and development servers using
Nagios,Icinga & Ganglia.
-
- Checking the security alerts and threats in the Nagios
and clear those alerts.
-
- Disk Management using LVM- add, remove PVs, Extending
LVs, and Moving PVs.
-
- Managing Remote servers and ensuring their uptime and
availability
-
- File System issues- Creating, mounting and extending file
systems, high utilization issues.
-
- Secure Remote Logins, File Copying and Granting File
access permissions.
-
- Troubleshooting and Maintenance Client and Server
Systems.
-
- Check the customer accounts on Database and update the
accounts according the requests.
-
- Ticket Management and resolution using the tools like SBM
,RT & JIRA.
-
- Decommissioning of old /unused servers.
-
- Experience on creating Virtual Machines, Install
operating systems inside VM's and install tools and configure these VM's based on requirements.
-
- Manage Virtual Machines on Vmware Environment using
Vmware Vsphere Client 5.0.
-
- Installing, Configuring and administering VMware ESXi and
vSphere Environment.
-
- Creating templates and deploying templates to the VM's.
-
- Taking snapshots of VM's and increasing the server drive
space without downtime.
-
- Troubleshoot ESXi Server and Virtual machine related
performance issues.
-
- Understanding and Working Knowledge on RAID concepts and
Administration.
-
- Basic Knowledge on Scripting.
-
- F5 Bigip virtual server pool's ,irules and hosts
management
-
- Schedule and execute cron jobs.
-
- Interacted with the engineering teams for product
support, improved and automated deployment and release processes.
-
- 24/7 On-call Support.
-
- Provide a documentation about the problem description and
the actions taken to fix the issue.
-
February 2010 - February 2017
Linux Admin
SIFY Technologies, Hyderabad
- Worked as Linux Admin supporting and maintaining the
website sify.com
-
- Installation, configurations and system administration on
Linux servers.
-
- Managing groups and user accounts assigned permissions to
users.
-
- Monitor error logs and troubleshoot the issues.
-
- Monitor system performance by using various utility like
Netstat.
-
- Updating and closing the tickets as per SLA norms.
-
- Package management like Download,Compilation,Installation
by using RPM,YUM,Monitoring Client systems.
-
- Daily Health checks on all systems and sends to reports
to clients.
-
- Installing and creation of LVM partitions and maintaining
those according to the requirement.
-
- Maintaining resources access permission to different
users and groups.
-
- Technical support through remote assistance and
management.
-
September 2008 - October 2009


Changing a Layout
You may change the title and description for a layout. You may also attach different files. To change a layout, access the
Portfolio Layouts tool and follow these steps:
- If the Portfolio Layouts home page is not displayed, click the Reset button.
- Click the Revise link below the name of the layout you want to change. Sakai displays the Revise Layout screen.
- Change entries in the Display Name and Description boxes, as needed.
- To change the layout or preview file, click the Select File link for the appropriate box. When Sakai displays the Select Item
screen, select the file you need by following the instructions for selecting an item. After you click Finish, Sakai displays
the Add Layout screen again. The name of the file you selected is shown in the box.
- Select the XHTML file you need by following the instructions for selecting an item. After you click Finish, Sakai displays
the Add Layout screen again. The name of the file you selected is shown in the box.
- Click the Save Changes button. Sakai makes the changes and displays the list on the Portfolio Layouts home page. Or, to return
to the home page without changing the layout, click Cancel.


Welcome to the third project of the Machine Learning Engineer Nanodegree! In this notebook, some template code has already been provided for you, and it will be your job to implement the additional functionality necessary to successfully complete this project. Sections that begin with 'Implementation' in the header indicate that the following block of code will require additional functionality which you must provide. Instructions will be provided for each section and the specifics of the implementation are marked in the code block with a 'TODO'
statement. Please be sure to read the instructions carefully!
In addition to implementing code, there will be questions that you must answer which relate to the project and your implementation. Each section where you will answer a question is preceded by a 'Question X' header. Carefully read each question and provide thorough answers in the following text boxes that begin with 'Answer:'. Your project submission will be evaluated based on your answers to each of the questions and the implementation you provide.
Note: Code and Markdown cells can be executed using the Shift + Enter keyboard shortcut. In addition, Markdown cells can be edited by typically double-clicking the cell to enter edit mode.
In this project, you will analyze a dataset containing data on various customers' annual spending amounts (reported in monetary units) of diverse product categories for internal structure. One goal of this project is to best describe the variation in the different types of customers that a wholesale distributor interacts with. Doing so would equip the distributor with insight into how to best structure their delivery service to meet the needs of each customer.
The dataset for this project can be found on the UCI Machine Learning Repository. For the purposes of this project, the features 'Channel'
and 'Region'
will be excluded in the analysis — with focus instead on the six product categories recorded for customers.
Run the code block below to load the wholesale customers dataset, along with a few of the necessary Python libraries required for this project. You will know the dataset loaded successfully if the size of the dataset is reported.
In this section, you will begin exploring the data through visualizations and code to understand how each feature is related to the others. You will observe a statistical description of the dataset, consider the relevance of each feature, and select a few sample data points from the dataset which you will track through the course of this project.
Run the code block below to observe a statistical description of the dataset. Note that the dataset is composed of six important product categories: 'Fresh', 'Milk', 'Grocery', 'Frozen', 'Detergents_Paper', and 'Delicatessen'. Consider what each category represents in terms of products you could purchase.
# Import libraries necessary for this project
import numpy as np
import pandas as pd
from IPython.display import display # Allows the use of display() for DataFrames
# Import supplementary visualizations code visuals.py
import visuals as vs
# Pretty display for notebooks
%matplotlib inline
# Load the wholesale customers dataset
try:
data = pd.read_csv("customers.csv")
data.drop(['Region', 'Channel'], axis = 1, inplace = True)
print("Wholesale customers dataset has {} samples with {} features each.".format(*data.shape))
except:
print("Dataset could not be loaded. Is the dataset missing?")
# Display a description of the dataset
display(data.describe())
To get a better understanding of the customers and how their data will transform through the analysis, it would be best to select a few sample data points and explore them in more detail. In the code block below, add three indices of your choice to the indices
list which will represent the customers to track. It is suggested to try different sets of samples until you obtain customers that vary significantly from one another.
# TODO: Select three indices of your choice you wish to sample from the dataset
indices = [0,1,2]
# Create a DataFrame of the chosen samples
samples = pd.DataFrame(data.loc[indices], columns = data.keys()).reset_index(drop = True)
print("Chosen samples of wholesale customers dataset:")
display(samples)
Consider the total purchase cost of each product category and the statistical description of the dataset above for your sample customers.
Hint: Examples of establishments include places like markets, cafes, delis, wholesale retailers, among many others. Avoid using names for establishments, such as saying "McDonalds" when describing a sample customer as a restaurant. You can use the mean values for reference to compare your samples with. The mean values are as follows:
Knowing this, how do your samples compare? Does that help in driving your insight into what kind of establishments they might be?
display(samples - np.round(data.mean()))
display(samples - np.round(data.median()))
Answer:
One interesting thought to consider is if one (or more) of the six product categories is actually relevant for understanding customer purchasing. That is to say, is it possible to determine whether customers purchasing some amount of one category of products will necessarily purchase some proportional amount of another category of products? We can make this determination quite easily by training a supervised regression learner on a subset of the data with one feature removed, and then score how well that model can predict the removed feature.
In the code block below, you will need to implement the following:
new_data
a copy of the data by removing a feature of your choice using the DataFrame.drop
function.sklearn.cross_validation.train_test_split
to split the dataset into training and testing sets.test_size
of 0.25
and set a random_state
.random_state
, and fit the learner to the training data.score
function.# TODO: Make a copy of the DataFrame, using the 'drop' function to drop the given feature
from sklearn.model_selection import train_test_split
from sklearn.tree import DecisionTreeRegressor
grocery = data['Grocery']
new_data = data.drop(['Grocery'], axis = 1, inplace = False)
# TODO: Split the data into training and testing sets(0.25) using the given feature as the target
# Set a random state.
X_train, X_test, y_train, y_test = train_test_split(new_data, grocery, test_size = 0.25, random_state = 1)
# TODO: Create a decision tree regressor and fit it to the training set
regressor = DecisionTreeRegressor(random_state = 1)
regressor.fit(X_train, y_train)
# TODO: Report the score of the prediction using the testing set
score = regressor.score(X_test, y_test)
print(score)
Hint: The coefficient of determination, R^2
, is scored between 0 and 1, with 1 being a perfect fit. A negative R^2
implies the model fails to fit the data. If you get a low score for a particular feature, that lends us to beleive that that feature point is hard to predict using the other features, thereby making it an important feature to consider when considering relevance.
Answer:
To get a better understanding of the dataset, we can construct a scatter matrix of each of the six product features present in the data. If you found that the feature you attempted to predict above is relevant for identifying a specific customer, then the scatter matrix below may not show any correlation between that feature and the others. Conversely, if you believe that feature is not relevant for identifying a specific customer, the scatter matrix might show a correlation between that feature and another feature in the data. Run the code block below to produce a scatter matrix.
# Produce a scatter matrix for each pair of features in the data
pd.plotting.scatter_matrix(data, alpha = 0.3, figsize = (14,8), diagonal = 'kde');
Hint: Is the data normally distributed? Where do most of the data points lie? You can use corr() to get the feature correlations and then visualize them using a heatmap(the data that would be fed into the heatmap would be the correlation values, for eg: data.corr()
) to gain further insight.
correlation = data.corr(method='pearson')
display(correlation)
import seaborn as sns
heatmap = sns.heatmap(correlation, annot=True)
Answer:
In this section, you will preprocess the data to create a better representation of customers by performing a scaling on the data and detecting (and optionally removing) outliers. Preprocessing data is often times a critical step in assuring that results you obtain from your analysis are significant and meaningful.
If data is not normally distributed, especially if the mean and median vary significantly (indicating a large skew), it is most often appropriate to apply a non-linear scaling — particularly for financial data. One way to achieve this scaling is by using a Box-Cox test, which calculates the best power transformation of the data that reduces skewness. A simpler approach which can work in most cases would be applying the natural logarithm.
In the code block below, you will need to implement the following:
log_data
after applying logarithmic scaling. Use the np.log
function for this.log_samples
after applying logarithmic scaling. Again, use np.log
.# TODO: Scale the data using the natural logarithm
log_data = np.log(data)
# TODO: Scale the sample data using the natural logarithm
log_samples = np.log(samples)
# Produce a scatter matrix for each pair of newly-transformed features
pd.plotting.scatter_matrix(log_data, alpha = 0.3, figsize = (14,8), diagonal = 'kde');
After applying a natural logarithm scaling to the data, the distribution of each feature should appear much more normal. For any pairs of features you may have identified earlier as being correlated, observe here whether that correlation is still present (and whether it is now stronger or weaker than before).
Run the code below to see how the sample data has changed after having the natural logarithm applied to it.
# Display the log-transformed sample data
display(log_samples)
Detecting outliers in the data is extremely important in the data preprocessing step of any analysis. The presence of outliers can often skew results which take into consideration these data points. There are many "rules of thumb" for what constitutes an outlier in a dataset. Here, we will use Tukey's Method for identfying outliers: An outlier step is calculated as 1.5 times the interquartile range (IQR). A data point with a feature that is beyond an outlier step outside of the IQR for that feature is considered abnormal.
In the code block below, you will need to implement the following:
Q1
. Use np.percentile
for this.Q3
. Again, use np.percentile
.step
.outliers
list.NOTE: If you choose to remove any outliers, ensure that the sample data does not contain any of these points!
Once you have performed this implementation, the dataset will be stored in the variable good_data
.
# For each feature find the data points with extreme high or low values
for feature in log_data.keys():
# TODO: Calculate Q1 (25th percentile of the data) for the given feature
Q1 = np.percentile(log_data[feature], q=25)
# TODO: Calculate Q3 (75th percentile of the data) for the given feature
Q3 = np.percentile(log_data[feature], q=75)
# TODO: Use the interquartile range to calculate an outlier step (1.5 times the interquartile range)
interquartile_range = Q3 - Q1
step = 1.5 * interquartile_range
# Display the outliers
print("Data points considered outliers for the feature '{}':".format(feature))
display(log_data[~((log_data[feature] >= Q1 - step) & (log_data[feature] <= Q3 + step))])
# OPTIONAL: Select the indices for data points you wish to remove
outliers = [65, 66, 304, 128, 154, 75, 357, 86, 356, 38 ,57, 145, 325, 429, 285, 289]
# Remove the outliers, if any were specified
good_data = log_data.drop(log_data.index[outliers]).reset_index(drop = True)
outliers
list to be removed, explain why.Hint: If you have datapoints that are outliers in multiple categories think about why that may be and if they warrant removal. Also note how k-means is affected by outliers and whether or not this plays a factor in your analysis of whether or not to remove them.
Answer:
In this section you will use principal component analysis (PCA) to draw conclusions about the underlying structure of the wholesale customer data. Since using PCA on a dataset calculates the dimensions which best maximize variance, we will find which compound combinations of features best describe customers.
Now that the data has been scaled to a more normal distribution and has had any necessary outliers removed, we can now apply PCA to the good_data
to discover which dimensions about the data best maximize the variance of features involved. In addition to finding these dimensions, PCA will also report the explained variance ratio of each dimension — how much variance within the data is explained by that dimension alone. Note that a component (dimension) from PCA can be considered a new "feature" of the space, however it is a composition of the original features present in the data.
In the code block below, you will need to implement the following:
sklearn.decomposition.PCA
and assign the results of fitting PCA in six dimensions with good_data
to pca
.log_samples
using pca.transform
, and assign the results to pca_samples
.# TODO: Apply PCA by fitting the good data with the same number of dimensions as features
from sklearn.decomposition import PCA
pca = PCA(n_components=6)
pca.fit(good_data)
# TODO: Transform log_samples using the PCA fit above
pca_samples = pca.transform(log_samples)
print(pca.explained_variance_ratio_)
# Generate PCA results plot
pca_results = vs.pca_results(good_data, pca)
Hint: A positive increase in a specific dimension corresponds with an increase of the positive-weighted features and a decrease of the negative-weighted features. The rate of increase or decrease is based on the individual feature weights.
Answer:
The graph confirms my initial suspicions.
For example, a higher spending on Grocery indicates a high spending on Milk and Detergents_Paper as well. So the first component could represent retail chains very well.
Run the code below to see how the log-transformed sample data has changed after having a PCA transformation applied to it in six dimensions. Observe the numerical value for the first four dimensions of the sample points. Consider if this is consistent with your initial interpretation of the sample points.
# Display sample log-data after having a PCA transformation applied
display(pd.DataFrame(np.round(pca_samples, 4), columns = pca_results.index.values))
When using principal component analysis, one of the main goals is to reduce the dimensionality of the data — in effect, reducing the complexity of the problem. Dimensionality reduction comes at a cost: Fewer dimensions used implies less of the total variance in the data is being explained. Because of this, the cumulative explained variance ratio is extremely important for knowing how many dimensions are necessary for the problem. Additionally, if a signifiant amount of variance is explained by only two or three dimensions, the reduced data can be visualized afterwards.
In the code block below, you will need to implement the following:
good_data
to pca
.good_data
using pca.transform
, and assign the results to reduced_data
.log_samples
using pca.transform
, and assign the results to pca_samples
.# TODO: Apply PCA by fitting the good data with only two dimensions
pca = PCA(n_components=2)
pca.fit(good_data)
# TODO: Transform the good data using the PCA fit above
reduced_data = pca.transform(good_data)
# TODO: Transform log_samples using the PCA fit above
pca_samples = pca.transform(log_samples)
# Create a DataFrame for the reduced data
reduced_data = pd.DataFrame(reduced_data, columns = ['Dimension 1', 'Dimension 2'])
Run the code below to see how the log-transformed sample data has changed after having a PCA transformation applied to it using only two dimensions. Observe how the values for the first two dimensions remains unchanged when compared to a PCA transformation in six dimensions.
# Display sample log-data after applying PCA transformation in two dimensions
display(pd.DataFrame(np.round(pca_samples, 4), columns = ['Dimension 1', 'Dimension 2']))
A biplot is a scatterplot where each data point is represented by its scores along the principal components. The axes are the principal components (in this case Dimension 1
and Dimension 2
). In addition, the biplot shows the projection of the original features along the components. A biplot can help us interpret the reduced dimensions of the data, and discover relationships between the principal components and original features.
Run the code cell below to produce a biplot of the reduced-dimension data.
# Create a biplot
vs.biplot(good_data, reduced_data, pca)
Once we have the original feature projections (in red), it is easier to interpret the relative position of each data point in the scatterplot. For instance, a point the lower right corner of the figure will likely correspond to a customer that spends a lot on 'Milk'
, 'Grocery'
and 'Detergents_Paper'
, but not so much on the other product categories.
From the biplot, which of the original features are most strongly correlated with the first component? What about those that are associated with the second component? Do these observations agree with the pca_results plot you obtained earlier?
In this section, you will choose to use either a K-Means clustering algorithm or a Gaussian Mixture Model clustering algorithm to identify the various customer segments hidden in the data. You will then recover specific data points from the clusters to understand their significance by transforming them back into their original dimension and scale.
Hint: Think about the differences between hard clustering and soft clustering and which would be appropriate for our dataset.
Answer:
Advantages of K-Means Clustering:
Advantages of Gaussian Mixture Clustering:
I would go with soft (fuzzy) clustering, as from our data-set it appears that different customers have similar purchasing patterns. Also, fuzzy clustering seems to yield better results, as researched in this research paper.
Depending on the problem, the number of clusters that you expect to be in the data may already be known. When the number of clusters is not known a priori, there is no guarantee that a given number of clusters best segments the data, since it is unclear what structure exists in the data — if any. However, we can quantify the "goodness" of a clustering by calculating each data point's silhouette coefficient. The silhouette coefficient for a data point measures how similar it is to its assigned cluster from -1 (dissimilar) to 1 (similar). Calculating the mean silhouette coefficient provides for a simple scoring method of a given clustering.
In the code block below, you will need to implement the following:
reduced_data
and assign it to clusterer
.reduced_data
using clusterer.predict
and assign them to preds
.centers
.pca_samples
and assign them sample_preds
.sklearn.metrics.silhouette_score
and calculate the silhouette score of reduced_data
against preds
.score
and print the result.# TODO: Apply your clustering algorithm of choice to the reduced data
from sklearn.mixture import GaussianMixture
from sklearn.metrics import silhouette_score
n_clusters_range = [2,3,4,5,6]
# TODO: Predict the cluster for each data point
for n_clusters in n_clusters_range:
clusterer = GaussianMixture(n_components=n_clusters) #Initializes the clusterer
clusterer.fit(reduced_data)
preds = clusterer.predict(reduced_data)
# TODO: Find the cluster centers
centers = clusterer.means_
# TODO: Predict the cluster for each transformed sample data point
sample_preds = clusterer.predict(pca_samples)
# TODO: Calculate the mean silhouette coefficient for the number of clusters chosen
score = silhouette_score(reduced_data, preds)
print(score)
Answer:
These are the scores for cluster numbers 2,3,4,5,6 -
Of these, cluster numbers 2 and 3 have the best silhouette scores
Once you've chosen the optimal number of clusters for your clustering algorithm using the scoring metric above, you can now visualize the results by executing the code block below. Note that, for experimentation purposes, you are welcome to adjust the number of clusters for your clustering algorithm to see various visualizations. The final visualization provided should, however, correspond with the optimal number of clusters.
# Display the results of the clustering from implementation
vs.cluster_results(reduced_data, preds, centers, pca_samples)
optimum_clusters = 2
optimum_clusterer = GaussianMixture(n_components=optimum_clusters)
optimum_clusterer.fit(reduced_data)
preds = optimum_clusterer.predict(reduced_data)
sample_preds = optimum_clusterer.predict(pca_samples)
centers = optimum_clusterer.means_
vs.cluster_results(reduced_data, preds, centers, pca_samples)
Each cluster present in the visualization above has a central point. These centers (or means) are not specifically data points from the data, but rather the averages of all the data points predicted in the respective clusters. For the problem of creating customer segments, a cluster's center point corresponds to the average customer of that segment. Since the data is currently reduced in dimension and scaled by a logarithm, we can recover the representative customer spending from these data points by applying the inverse transformations.
In the code block below, you will need to implement the following:
centers
using pca.inverse_transform
and assign the new centers to log_centers
.np.log
to log_centers
using np.exp
and assign the true centers to true_centers
.# TODO: Inverse transform the centers
log_centers = pca.inverse_transform(centers)
# TODO: Exponentiate the centers
true_centers = np.exp(log_centers)
# Display the true centers
segments = ['Segment {}'.format(i) for i in range(0,len(centers))]
true_centers = pd.DataFrame(np.round(true_centers), columns = data.keys())
true_centers.index = segments
display(true_centers)
Adding a bar plot to help compare each product to the mean/median values
true_centers = true_centers.append(data.describe().loc['50%'])
true_centers.plot(kind = 'bar', figsize = (16, 4))
Hint: A customer who is assigned to 'Cluster X'
should best identify with the establishments represented by the feature set of 'Segment X'
. Think about what each segment represents in terms their values for the feature points chosen. Reference these values with the mean values to get some perspective into what kind of establishment they represent.
Answer:
For the first Segment,there appears to be high number of orders for Milk and Grocery, so this indicates that it could be a restaurant
The second segment has more of Fresh orders, so this could be a vegetables supermarket. However, restaurants also buy lot of vegetables.
So there's a high likelihood of both the data points being clustered together.
Run the code block below to find which cluster each sample point is predicted to be.
# Display the predictions
for i, pred in enumerate(sample_preds):
print("Sample point", i, "predicted to be in Cluster", pred)
Answer:
In this final section, you will investigate ways that you can make use of the clustered data. First, you will consider how the different groups of customers, the customer segments, may be affected differently by a specific delivery scheme. Next, you will consider how giving a label to each customer (which segment that customer belongs to) can provide for additional features about the customer data. Finally, you will compare the customer segments to a hidden variable present in the data, to see whether the clustering identified certain relationships.
Companies will often run A/B tests when making small changes to their products or services to determine whether making that change will affect its customers positively or negatively. The wholesale distributor is considering changing its delivery service from currently 5 days a week to 3 days a week. However, the distributor will only make this change in delivery service for customers that react positively.
Hint: Can we assume the change affects all customers equally? How can we determine which group of customers it affects the most?
Answer:
The distributor now knows that retail stores and restaurants will be affected, since they do have orders for lot of perishable commodities, like Milk, Fresh and Grocery. These are items that people consume on a daily basis, so it's important for the distributor to understand that these customers might react negatively.
On the other hand, other customers who have more orders in the other features would react positively.
If we assume two customer segments - retails/supermarkets and restaurants - these both will get affected the most equally.
For A/B testing, I hypothesize this - having two control groups, with a mixture of customer segments in each. One group might have customers that lie closer to the mean/median of the order distributions and they could have deliveries for 3 days a week. While the other group could be serviced for 5 days a week. This will help in eliminating any outliers from the control groups. Data collected from these control groups, like the average conversion rates and reviews will help the distributor understand the reactions in each customer segment.
Additional structure is derived from originally unlabeled data when using clustering techniques. Since each customer has a customer segment it best identifies with (depending on the clustering algorithm applied), we can consider 'customer segment' as an engineered feature for the data. Assume the wholesale distributor recently acquired ten new customers and each provided estimates for anticipated annual spending of each product category. Knowing these estimates, the wholesale distributor wants to classify each new customer to a customer segment to determine the most appropriate delivery service.
Hint: A supervised learner could be used to train on the original customers. What would be the target variable?
Answer:
The wholesale distributor can now classify all their customers under two broad categories - retails/supermarkets and restaurants. Given that the distributor knows the order patterns for each customer segment and also has the annual spending estimates, this knowledge can be used to figure out which category the customers belong to.
If we use supervised learning, then the target variable could be whether the customers belong to one category or another.
At the beginning of this project, it was discussed that the 'Channel'
and 'Region'
features would be excluded from the dataset so that the customer product categories were emphasized in the analysis. By reintroducing the 'Channel'
feature to the dataset, an interesting structure emerges when considering the same PCA dimensionality reduction applied earlier to the original dataset.
Run the code block below to see how each data point is labeled either 'HoReCa'
(Hotel/Restaurant/Cafe) or 'Retail'
the reduced space. In addition, you will find the sample points are circled in the plot, which will identify their labeling.
# Display the clustering results based on 'Channel' data
vs.channel_results(reduced_data, outliers, pca_samples)
Answer:
Note: Once you have completed all of the code implementations and successfully answered each question above, you may finalize your work by exporting the iPython Notebook as an HTML document. You can do this by using the menu above and navigating to
File -> Download as -> HTML (.html). Include the finished document along with this notebook as your submission.


| Interface | Description |
|---|---|
| BarbelProxy |
The target proxy interface applied to POJOs when running in
BarbelMode.POJO . |
| Bitemporal |
Interface applied to all objects managed by
BarbelHisto . |
| UpdateCaseAware |
| Class | Description |
|---|---|
| BitemporalStamp |
Abstraction to carry the bitemporal data for each individual version.
|
| BitemporalStamp.Builder |
Builder to build
BitemporalStamp . |
| BitemporalVersion |
Class used by
BarbelHisto in BarbelMode.POJO to persist data
to persistent storage. |
| DefaultDocument |
A fully equipped example implementation for business classes managed by
BarbelHisto . |
| DefaultDocument.Builder |
Builder to build
DefaultDocument . |
| DefaultPojo | |
| EffectivePeriod |
The abstraction storing the effective time for a version.
|
| RecordPeriod |
The abstraction for storing the record time details of a version.
|
| RecordPeriod.Builder | |
| Systemclock |
BarbelHisto s clock implementation. |
| Enum | Description |
|---|---|
| BitemporalObjectState |
Versions have two main states: active means they are valid from a business
viewpoint.
|
Copyright © 2019 Project Barbel. All rights reserved.


Provides a graphics output device for R that records plots
in a LaTeX-friendly format. The device transforms plotting
commands issued by R functions into LaTeX code blocks. When
included in a LaTeX document, these blocks are interpreted with
the help of 'TikZ'—a graphics package for TeX and friends
written by Till Tantau. Using the 'tikzDevice', the text of R
plots can contain LaTeX commands such as mathematical formula.
The device also allows arbitrary LaTeX code to be inserted into
the output stream.
| Version: |
0.12 |
| Depends: |
R (≥ 2.14.0) |
| Imports: |
filehash (≥ 2.3), png |
| Suggests: |
evaluate, formatR, ggplot2, knitr, lattice, maps, scales, stringr, testthat (≥ 0.8.1), withr |
| Published: |
2018-07-02 |
| Author: |
Charlie Sharpsteen [aut],
Cameron Bracken [aut],
Kirill Müller [ctb],
Yihui Xie [ctb],
Ralf Stubner [cre] |
| Maintainer: |
Ralf Stubner <ralf.stubner at daqana.com> |
| BugReports: |
https://github.com/daqana/tikzDevice/issues |
| License: |
GPL-2 | GPL-3 [expanded from: GPL (≥ 2)] |
| URL: |
https://github.com/daqana/tikzDevice |
| NeedsCompilation: |
yes |
| SystemRequirements: |
pgf (>= 2.00) |
| Materials: |
NEWS |
| In views: |
ReproducibleResearch |
| CRAN checks: |
tikzDevice results |


S3 Cloudfront Static Site
Confession: I struggle with AWS services, in that I don’t find them that intuitive to use, and mostly default to bouncing around trying to figure out which switches and dials to tweak in order to derive a desirable result.
That said, the complexity results in the ability to build some powerful services pretty darn quickly when compared with attempting to orchestrate similar solutions on your own.
My most recent foray into AWS (outside of the office) was getting this site running. I’d previously hosted iterations of it on a Digital Ocean Kubernetes cluster, but ultimately figured that spending in excess of $40 per month on a site that nobody reads a bit silly. Next, I went for a GitHub Pages derivative. That just works, but when considering things to play with the future, I figured that I’d end up running some services out of AWS anyway…so why not just run the site there?
The concept of running a static site on S3 is not new, nor is the idea of fronting it with a CloudFront distribution. What I hadn’t figured on was just how much time I’d spend scratching my head saying “wut?” while getting it going.
Here’s what I ended up with.
Route53
This is relatively simple. Once you have CloudFront configured, you’re going to
be using alias
records which point your apex and a www
record to CF.
S3
I created two buckets. One is called www.nosignal.io
and simply redirects traffic
to the primary bucket that contains the code, called nosignal.io
.
Under properties for www.nosignal.io
, Static website hosting is enabled,
with Redirect requests set to:
Target bucket or domain: nosignal.io
Protocol: https
The properties for nosignal.io
have Use this bucket to host a website set,
with the index document
and error document
properties set.
Under permissions (for both buckets), I have Block all public access enabled. The only service that I want to be able to access my content is CloudFront. This should reduce the risk of any silliness whereby content could be pulled from S3 in sufficient enough volumes to cause me any financial misery, and means that anything added to S3 is only accessible via the CDN that CloudFront provides.
Under Permissions, I have the Canonical ID of the S3 Origin from CloudFront set to List Objects. This effectively allows CloudFront read access to the bucket.
Under Bucket Policy, I have the following:
{
"Version": "2012-10-17",
"Id": "PolicyForCloudFrontPrivateContent",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"AWS": "arn:aws:iam::cloudfront:user/CloudFront Origin Access Identity XXXXXXXXXXXXXX"
},
"Action": "s3:GetObject",
"Resource": "arn:aws:s3:::nosignal.io/*"
}
]
}
CloudFront
I opted for a single CloudFront distribution that uses all edge locations and has
CNAMEs
configured for nosignal.io
and www.nosignal.io
. After multiple bites
of the cherry in getting AWS Certificate Manager to issue a cert and then use it
in my CloudFront distribution, I ultimately ended up using the Distribution creation
wizard to request a certificate (also mapped to the apex and www
names of my site).
Another tweak was to set the Security Policy to TLSv1.2_2018 and above, as well
as set the Default Root Object
to index.html
.
Under Origins and Origin Groups, I have nosignal.io.s3.amazonaws.com
and
www.nosignal.io.s3.amazonaws.com
which map to their respective Origin Domain
Names and use an identity created (AFAIK) during the creation of the Distribution.
Withion Behaviors I have a single Default (*)
behaviour that maps to the
S3 bucket of my apex domain (which contains all of the content).
It is under Origin Access Identity under CF that you can find the
Amazon S3 Canonical User ID
I references under S3 > Permissions
to allow
CF originated requests read access to the S3 buckets.
Fixing Directory Indexing
When you direct requests to an S3 bucket from CloudFront, those requests don’t
read the objects from your bucket, they’re fetched from the S3 REST API. For this
reason, a request to /about/
will read from /about/index.html
, but fails to
render as CloudFront isn’t reading the file, it’s reading an index.html
object
hanging off of the about
object from an API request. To get around this, you
can either switch off the protections that make CloudFront the default read
resource for your bucket, or you can enable uglyurls
in Hugo, or you can set up
a Lambda@Edge function to handle the request translation for you.
I opted for a Lambda@Edge function. The basic code (direct from AWS) looks as follows:
'use strict';
exports.handler = (event, context, callback) => {
// Extract the request from the CloudFront event that is sent to Lambda@Edge
var request = event.Records[0].cf.request;
// Extract the URI from the request
var olduri = request.uri;
// Match any '/' that occurs at the end of a URI. Replace it with a default index
var newuri = olduri.replace(/\/$/, '\/index.html');
// Log the URI as received by CloudFront and the new URI to be used to fetch from origin
console.log("Old URI: " + olduri);
console.log("New URI: " + newuri);
// Replace the received URI with the URI that includes the index page
request.uri = newuri;
// Return to CloudFront
return callback(null, request);
};
It simply plugs index.html
onto the end of a request so that the required
object can be rendered in the browser.
To set one up, make sure that your region is US East (N. Virginia). Any other region won’t show the required CloudFront trigger. Head over to Lambda and create a new function. Choose Author from scratch, name your function, choose Node.js 10.x as your runtime and then select Create a new role from AWS policy templates. Give your new role a name, and then select Basic Lambda@Edge permissions (for CloudFront tigger) and select Create Function.
Once the designer screen opens, click Add trigger and select CloudFront. Then
select Deploy to Lambda@Edge. This will create a layer in the Designer view
named after your function. Paste the code above into the index.js
editor
window and save your code. You can then click on the Actions drop down and
select Deploy to Lambda@Edge. You may as well wander off at this point,
as your CloudFront Distribution is kicking off an update. As soon as your
Distribution has been updated, your site should be working as expected.
In summary
It took me a couple of hours to figure out S3 + AWS Certificate Manager +
CloudFront + Lambda@Edge. Getting this done as a GitHub Pages site with an SSL
cert mapped to my custom domain takes a few minutes. Even getting this done on a
three node k8s cluster on DigitalOcean with some scripts to turn a hugo
build
command into content on a custom Nginx image took a day of fiddling, and that
included writing all of the YAML, getting Nginx ingress working and hooking up
cert-manager.
So where’s the benefit to this? My job here is now done. I have no further
maintenance to undertake. My site is deployed on the CDN of one of the largest
networks on the planet. It’s delivered over HTTPS. I haven’t had to open my
S3 bucket to the world. If I ever write something that ends up on the front page
of Hacker News, I don’t need to think about scale.
If I decided to muck around with some JavaScript to talk to backend services,
I have one of the largest toolboxes of toys to leverage. Going forward,
updates are as simple as write
→ hugo server -D
→ hugo
→ hugo deploy
.
Probably.


Conversion and Promotion¶
Julia has a system for promoting arguments of mathematical operators to a common type, which has been mentioned in various other sections, including 정수와 부동소수점으로 표현되는 실수, 수학 연산들과 기본적인 함수들, Types, and Methods. In this section, we explain how this promotion system works, as well as how to extend it to new types and apply it to functions besides built-in mathematical operators. Traditionally, programming languages fall into two camps with respect to promotion of arithmetic arguments:
- Automatic promotion for built-in arithmetic types and operators.
In most languages, built-in numeric types, when used as operands to
arithmetic operators with infix syntax, such as
+
,-
,*
, and/
, are automatically promoted to a common type to produce the expected results. C, Java, Perl, and Python, to name a few, all correctly compute the sum1 + 1.5
as the floating-point value2.5
, even though one of the operands to+
is an integer. These systems are convenient and designed carefully enough that they are generally all-but-invisible to the programmer: hardly anyone consciously thinks of this promotion taking place when writing such an expression, but compilers and interpreters must perform conversion before addition since integers and floating-point values cannot be added as-is. Complex rules for such automatic conversions are thus inevitably part of specifications and implementations for such languages. - No automatic promotion. This camp includes Ada and ML — very
“strict” statically typed languages. In these languages, every
conversion must be explicitly specified by the programmer. Thus, the
example expression
1 + 1.5
would be a compilation error in both Ada and ML. Instead one must writereal(1) + 1.5
, explicitly converting the integer1
to a floating-point value before performing addition. Explicit conversion everywhere is so inconvenient, however, that even Ada has some degree of automatic conversion: integer literals are promoted to the expected integer type automatically, and floating-point literals are similarly promoted to appropriate floating-point types.
In a sense, Julia falls into the “no automatic promotion” category: mathematical operators are just functions with special syntax, and the arguments of functions are never automatically converted. However, one may observe that applying mathematical operations to a wide variety of mixed argument types is just an extreme case of polymorphic multiple dispatch — something which Julia’s dispatch and type systems are particularly well-suited to handle. “Automatic” promotion of mathematical operands simply emerges as a special application: Julia comes with pre-defined catch-all dispatch rules for mathematical operators, invoked when no specific implementation exists for some combination of operand types. These catch-all rules first promote all operands to a common type using user-definable promotion rules, and then invoke a specialized implementation of the operator in question for the resulting values, now of the same type. User-defined types can easily participate in this promotion system by defining methods for conversion to and from other types, and providing a handful of promotion rules defining what types they should promote to when mixed with other types.
Conversion¶
Conversion of values to various types is performed by the convert
function. The convert
function generally takes two arguments: the
first is a type object while the second is a value to convert to that
type; the returned value is the value converted to an instance of given
type. The simplest way to understand this function is to see it in
action:
julia> x = 12
12
julia> typeof(x)
Int64
julia> convert(UInt8, x)
0x0c
julia> typeof(ans)
UInt8
julia> convert(AbstractFloat, x)
12.0
julia> typeof(ans)
Float64
julia> a = Any[1 2 3; 4 5 6]
2x3 Array{Any,2}:
1 2 3
4 5 6
julia> convert(Array{Float64}, a)
2x3 Array{Float64,2}:
1.0 2.0 3.0
4.0 5.0 6.0
Conversion isn’t always possible, in which case a no method error is
thrown indicating that convert
doesn’t know how to perform the
requested conversion:
julia> convert(AbstractFloat, "foo")
ERROR: MethodError: Cannot `convert` an object of type String to an object of type AbstractFloat
This may have arisen from a call to the constructor AbstractFloat(...),
since type constructors fall back to convert methods.
...
Some languages consider parsing strings as numbers or formatting
numbers as strings to be conversions (many dynamic languages will even
perform conversion for you automatically), however Julia does not: even
though some strings can be parsed as numbers, most strings are not valid
representations of numbers, and only a very limited subset of them are.
Therefore in Julia the dedicated parse()
function must be used
to perform this operation, making it more explicit.
Defining New Conversions¶
To define a new conversion, simply provide a new method for convert()
.
That’s really all there is to it. For example, the method to convert a
real number to a boolean is this:
convert(::Type{Bool}, x::Real) = x==0 ? false : x==1 ? true : throw(InexactError())
The type of the first argument of this method is a singleton
type, Type{Bool}
, the only instance of
which is Bool
. Thus, this method is only invoked when the first
argument is the type value Bool
. Notice the syntax used for the first
argument: the argument name is omitted prior to the ::
symbol, and only
the type is given. This is the syntax in Julia for a function argument whose type is
specified but whose value is never used in the function body. In this example,
since the type is a singleton, there would never be any reason to use its value
within the body.
When invoked, the method determines
whether a numeric value is true or false as a boolean, by comparing it
to one and zero:
julia> convert(Bool, 1)
true
julia> convert(Bool, 0)
false
julia> convert(Bool, 1im)
ERROR: InexactError()
in convert(::Type{Bool}, ::Complex{Int64}) at ./complex.jl:23
...
julia> convert(Bool, 0im)
false
The method signatures for conversion methods are often quite a bit more involved than this example, especially for parametric types. The example above is meant to be pedagogical, and is not the actual Julia behaviour. This is the actual implementation in Julia:
convert{T<:Real}(::Type{T}, z::Complex) = (imag(z)==0 ? convert(T,real(z)) :
throw(InexactError()))
julia> convert(Bool, 1im)
ERROR: InexactError()
in convert(::Type{Bool}, ::Complex{Int64}) at ./complex.jl:18
...
Case Study: Rational Conversions¶
To continue our case study of Julia’s Rational
type, here are the
conversions declared in
rational.jl,
right after the declaration of the type and its constructors:
convert{T<:Integer}(::Type{Rational{T}}, x::Rational) = Rational(convert(T,x.num),convert(T,x.den))
convert{T<:Integer}(::Type{Rational{T}}, x::Integer) = Rational(convert(T,x), convert(T,1))
function convert{T<:Integer}(::Type{Rational{T}}, x::AbstractFloat, tol::Real)
if isnan(x); return zero(T)//zero(T); end
if isinf(x); return sign(x)//zero(T); end
y = x
a = d = one(T)
b = c = zero(T)
while true
f = convert(T,round(y)); y -= f
a, b, c, d = f*a+c, f*b+d, a, b
if y == 0 || abs(a/b-x) <= tol
return a//b
end
y = 1/y
end
end
convert{T<:Integer}(rt::Type{Rational{T}}, x::AbstractFloat) = convert(rt,x,eps(x))
convert{T<:AbstractFloat}(::Type{T}, x::Rational) = convert(T,x.num)/convert(T,x.den)
convert{T<:Integer}(::Type{T}, x::Rational) = div(convert(T,x.num),convert(T,x.den))
The initial four convert methods provide conversions to rational types.
The first method converts one type of rational to another type of
rational by converting the numerator and denominator to the appropriate
integer type. The second method does the same conversion for integers by
taking the denominator to be 1. The third method implements a standard
algorithm for approximating a floating-point number by a ratio of
integers to within a given tolerance, and the fourth method applies it,
using machine epsilon at the given value as the threshold. In general,
one should have a//b == convert(Rational{Int64}, a/b)
.
The last two convert methods provide conversions from rational types to
floating-point and integer types. To convert to floating point, one
simply converts both numerator and denominator to that floating point
type and then divides. To convert to integer, one can use the div
operator for truncated integer division (rounded towards zero).
Promotion¶
Promotion refers to converting values of mixed types to a single common
type. Although it is not strictly necessary, it is generally implied
that the common type to which the values are converted can faithfully
represent all of the original values. In this sense, the term
“promotion” is appropriate since the values are converted to a “greater”
type — i.e. one which can represent all of the input values in a single
common type. It is important, however, not to confuse this with
object-oriented (structural) super-typing, or Julia’s notion of abstract
super-types: promotion has nothing to do with the type hierarchy, and
everything to do with converting between alternate representations. For
instance, although every Int32
value can also be represented as a
Float64
value, Int32
is not a subtype of Float64
.
Promotion to a common “greater” type is performed in Julia by the promote
function, which takes any number of arguments, and returns a tuple of
the same number of values, converted to a common type, or throws an
exception if promotion is not possible. The most common use case for
promotion is to convert numeric arguments to a common type:
julia> promote(1, 2.5)
(1.0,2.5)
julia> promote(1, 2.5, 3)
(1.0,2.5,3.0)
julia> promote(2, 3//4)
(2//1,3//4)
julia> promote(1, 2.5, 3, 3//4)
(1.0,2.5,3.0,0.75)
julia> promote(1.5, im)
(1.5 + 0.0im,0.0 + 1.0im)
julia> promote(1 + 2im, 3//4)
(1//1 + 2//1*im,3//4 + 0//1*im)
Floating-point values are promoted to the largest of the floating-point argument types. Integer values are promoted to the larger of either the native machine word size or the largest integer argument type. Mixtures of integers and floating-point values are promoted to a floating-point type big enough to hold all the values. Integers mixed with rationals are promoted to rationals. Rationals mixed with floats are promoted to floats. Complex values mixed with real values are promoted to the appropriate kind of complex value.
That is really all there is to using promotions. The rest is just a
matter of clever application, the most typical “clever” application
being the definition of catch-all methods for numeric operations like
the arithmetic operators +
, -
, *
and /
. Here are some of
the catch-all method definitions given in
promotion.jl:
+(x::Number, y::Number) = +(promote(x,y)...)
-(x::Number, y::Number) = -(promote(x,y)...)
*(x::Number, y::Number) = *(promote(x,y)...)
/(x::Number, y::Number) = /(promote(x,y)...)
In certain cases, the result type also depends on the operator;
such scenarios are handled by the promote_op
function.
These method definitions say that in the absence of more specific rules
for adding, subtracting, multiplying and dividing pairs of numeric
values, promote the values to a common type and then try again. That’s
all there is to it: nowhere else does one ever need to worry about
promotion to a common numeric type for arithmetic operations — it just
happens automatically. There are definitions of catch-all promotion
methods for a number of other arithmetic and mathematical functions in
promotion.jl,
but beyond that, there are hardly any calls to promote
required in
the Julia standard library. The most common usages of promote
occur
in outer constructors methods, provided for convenience, to allow
constructor calls with mixed types to delegate to an inner type with
fields promoted to an appropriate common type. For example, recall that
rational.jl
provides the following outer constructor method:
Rational(n::Integer, d::Integer) = Rational(promote(n,d)...)
This allows calls like the following to work:
julia> Rational(Int8(15),Int32(-5))
-3//1
julia> typeof(ans)
Rational{Int32}
For most user-defined types, it is better practice to require programmers to supply the expected types to constructor functions explicitly, but sometimes, especially for numeric problems, it can be convenient to do promotion automatically.
Defining Promotion Rules¶
Although one could, in principle, define methods for the promote
function directly, this would require many redundant definitions for all
possible permutations of argument types. Instead, the behavior of
promote
is defined in terms of an auxiliary function called
promote_rule
, which one can provide methods for. The
promote_rule
function takes a pair of type objects and returns
another type object, such that instances of the argument types will be
promoted to the returned type. Thus, by defining the rule:
promote_rule(::Type{Float64}, ::Type{Float32} ) = Float64
one declares that when 64-bit and 32-bit floating-point values are promoted together, they should be promoted to 64-bit floating-point. The promotion type does not need to be one of the argument types, however; the following promotion rules both occur in Julia’s standard library:
promote_rule(::Type{UInt8}, ::Type{Int8}) = Int
promote_rule(::Type{BigInt}, ::Type{Int8}) = BigInt
In the latter case, the result type is BigInt
since BigInt
is
the only type large enough to hold integers for arbitrary-precision
integer arithmetic. Also note that one does not need to define both
promote_rule(::Type{A}, ::Type{B})
and
promote_rule(::Type{B}, ::Type{A})
— the symmetry is implied by
the way promote_rule
is used in the promotion process.
The promote_rule
function is used as a building block to define a
second function called promote_type
, which, given any number of type
objects, returns the common type to which those values, as arguments to
promote
should be promoted. Thus, if one wants to know, in absence
of actual values, what type a collection of values of certain types
would promote to, one can use promote_type
:
julia> promote_type(Int8, UInt16)
Int64
Internally, promote_type
is used inside of promote
to determine
what type argument values should be converted to for promotion. It can,
however, be useful in its own right. The curious reader can read the
code in
promotion.jl,
which defines the complete promotion mechanism in about 35 lines.
Case Study: Rational Promotions¶
Finally, we finish off our ongoing case study of Julia’s rational number type, which makes relatively sophisticated use of the promotion mechanism with the following promotion rules:
promote_rule{T<:Integer}(::Type{Rational{T}}, ::Type{T}) = Rational{T}
promote_rule{T<:Integer,S<:Integer}(::Type{Rational{T}}, ::Type{S}) = Rational{promote_type(T,S)}
promote_rule{T<:Integer,S<:Integer}(::Type{Rational{T}}, ::Type{Rational{S}}) = Rational{promote_type(T,S)}
promote_rule{T<:Integer,S<:AbstractFloat}(::Type{Rational{T}}, ::Type{S}) = promote_type(T,S)
The first rule asserts that promotion of a rational number with its own numerator/denominator type, simply promotes to itself. The second rule says that promoting a rational number with any other integer type promotes to a rational type whose numerator/denominator type is the result of promotion of its numerator/denominator type with the other integer type. The third rule applies the same logic to two different types of rational numbers, resulting in a rational of the promotion of their respective numerator/denominator types. The fourth and final rule dictates that promoting a rational with a float results in the same type as promoting the numerator/denominator type with the float.
This small handful of promotion rules, together with the conversion methods discussed above, are sufficient to make rational numbers interoperate completely naturally with all of Julia’s other numeric types — integers, floating-point numbers, and complex numbers. By providing appropriate conversion methods and promotion rules in the same manner, any user-defined numeric type can interoperate just as naturally with Julia’s predefined numerics.