s React.js a library or a framework? In any case, it is a new way of working that represents a revolution in the way of building web projects. It has very particular characteristics that allow us, for instance, to render React code from the server side, or to include React components from Twig tags. During this talk we will present React.js, we will explore how to take advantage of it from PHP projects and we will give answers to practical problems such as universal (isomorphical) rendering and the generation of React.js forms from Symfony forms without duplication of efforts.
Паразитируем на React-экосистеме (Angular 4+) / Алексей Охрименко (IPONWEB)Ontico
РИТ++ 2017, Frontend Сonf
Зал Мумбаи, 5 июня, 13:00
Тезисы:
http://frontendconf.ru/2017/abstracts/2470.html
Паразитизм — форма взаимоотношений между организмами различных видов, из которых один (паразит — aka Angular 4+) использует другого (хозяина — aka React) в качестве среды обитания и источника питания, нанося ему вред, но при этом не убивая.
Паразитоид — организм, который проводит значительную часть своей жизни (в личиночной стадии), проживая на или внутри своего единственного хозяина, которого он постепенно убивает в процессе.
...
s React.js a library or a framework? In any case, it is a new way of working that represents a revolution in the way of building web projects. It has very particular characteristics that allow us, for instance, to render React code from the server side, or to include React components from Twig tags. During this talk we will present React.js, we will explore how to take advantage of it from PHP projects and we will give answers to practical problems such as universal (isomorphical) rendering and the generation of React.js forms from Symfony forms without duplication of efforts.
Паразитируем на React-экосистеме (Angular 4+) / Алексей Охрименко (IPONWEB)Ontico
РИТ++ 2017, Frontend Сonf
Зал Мумбаи, 5 июня, 13:00
Тезисы:
http://frontendconf.ru/2017/abstracts/2470.html
Паразитизм — форма взаимоотношений между организмами различных видов, из которых один (паразит — aka Angular 4+) использует другого (хозяина — aka React) в качестве среды обитания и источника питания, нанося ему вред, но при этом не убивая.
Паразитоид — организм, который проводит значительную часть своей жизни (в личиночной стадии), проживая на или внутри своего единственного хозяина, которого он постепенно убивает в процессе.
...
This is a presentation given by Dirk-Jan Rutten and Florentijn Hogerwerf at the React-Amsterdam Winter Event held on the 23rd of February 2017 (https://www.meetup.com/React-Amsterdam/events/237423993/).
In this talk I demonstrated how easy Dojo is integrating into the Adobe AIR runtime. Using a performance analysis tool I demonstrated how to use charting, grids and other features of Adobe AIR and the Dojo Toolkit
Talk on code and craftsmanship delivered at KCDC. It's best to approach code the way people traditionally learned crafts. Go through the stages of apprentice, journeyman, master. Along the way, develop your ability to see, your ability to create, and your understanding of why things work.
Basic Tutorial of React for ProgrammersDavid Rodenas
This is the support of a course to teach React programming for Java and C# programmers. It covers from its origins in Facebook til separation of presentational and container components. What is JSX, rules, state, props, refactoring, conditionals, repeats, forms, synchronizing values, composition, and so on.
Redux saga: managing your side effects. Also: generators in es6Ignacio Martín
Explanation of redux-saga for its use in React and React Native. Contains an explanation about ES6 generators, used in sagas, with emphasis in generators to manage async code.
This is a presentation given by Dirk-Jan Rutten and Florentijn Hogerwerf at the React-Amsterdam Winter Event held on the 23rd of February 2017 (https://www.meetup.com/React-Amsterdam/events/237423993/).
In this talk I demonstrated how easy Dojo is integrating into the Adobe AIR runtime. Using a performance analysis tool I demonstrated how to use charting, grids and other features of Adobe AIR and the Dojo Toolkit
Talk on code and craftsmanship delivered at KCDC. It's best to approach code the way people traditionally learned crafts. Go through the stages of apprentice, journeyman, master. Along the way, develop your ability to see, your ability to create, and your understanding of why things work.
Basic Tutorial of React for ProgrammersDavid Rodenas
This is the support of a course to teach React programming for Java and C# programmers. It covers from its origins in Facebook til separation of presentational and container components. What is JSX, rules, state, props, refactoring, conditionals, repeats, forms, synchronizing values, composition, and so on.
Redux saga: managing your side effects. Also: generators in es6Ignacio Martín
Explanation of redux-saga for its use in React and React Native. Contains an explanation about ES6 generators, used in sagas, with emphasis in generators to manage async code.
We're taking a closer look into a new utility class from Android Support Library. It enables you to calculate the difference between two lists and output a list of update operations swiftly and with style. Presented by Željko Plesac from Infinum.
Not so long ago Microsoft announced a new language trageting on front-end developers. Everybody's reaction was like: Why?!! Is it just Microsoft darting back to Google?!
So, why a new language? JavaScript has its bad parts. Mostly you can avoid them or workaraund. You can emulate class-based OOP style, modules, scoping and even run-time typing. But that is doomed to be clumsy. That's not in the language design. Google has pointed out these flaws, provided a new language and failed. Will the story of TypeScript be any different?
Do not repeat yourself, we teach every fledgling software developer. It makes sense as with growing code redundancy the maintenance cost increase. Simple tools such as functions or loops are a great ways to reduce code redundancy but in our quest to avoid code redundancy we sometimes indulge into complexity. Complex code is also costly to maintain. I will demonstrate, using real-world examples, how one can adopt metaprogramming to minimize code redundancy as well keeping the code simple enough for my mom to understand it.
Since these presentations were spare time hobby - I've decided to share them :)
Hopefully someone will find them useful.
This part continues 1. part with more design patterns like Command, State, NullObject.
Innovating Inference - Remote Triggering of Large Language Models on HPC Clus...Globus
Large Language Models (LLMs) are currently the center of attention in the tech world, particularly for their potential to advance research. In this presentation, we'll explore a straightforward and effective method for quickly initiating inference runs on supercomputers using the vLLM tool with Globus Compute, specifically on the Polaris system at ALCF. We'll begin by briefly discussing the popularity and applications of LLMs in various fields. Following this, we will introduce the vLLM tool, and explain how it integrates with Globus Compute to efficiently manage LLM operations on Polaris. Attendees will learn the practical aspects of setting up and remotely triggering LLMs from local machines, focusing on ease of use and efficiency. This talk is ideal for researchers and practitioners looking to leverage the power of LLMs in their work, offering a clear guide to harnessing supercomputing resources for quick and effective LLM inference.
Need for Speed: Removing speed bumps from your Symfony projects ⚡️Łukasz Chruściel
No one wants their application to drag like a car stuck in the slow lane! Yet it’s all too common to encounter bumpy, pothole-filled solutions that slow the speed of any application. Symfony apps are not an exception.
In this talk, I will take you for a spin around the performance racetrack. We’ll explore common pitfalls - those hidden potholes on your application that can cause unexpected slowdowns. Learn how to spot these performance bumps early, and more importantly, how to navigate around them to keep your application running at top speed.
We will focus in particular on tuning your engine at the application level, making the right adjustments to ensure that your system responds like a well-oiled, high-performance race car.
Enterprise Resource Planning System includes various modules that reduce any business's workload. Additionally, it organizes the workflows, which drives towards enhancing productivity. Here are a detailed explanation of the ERP modules. Going through the points will help you understand how the software is changing the work dynamics.
To know more details here: https://blogs.nyggs.com/nyggs/enterprise-resource-planning-erp-system-modules/
Essentials of Automations: The Art of Triggers and Actions in FMESafe Software
In this second installment of our Essentials of Automations webinar series, we’ll explore the landscape of triggers and actions, guiding you through the nuances of authoring and adapting workspaces for seamless automations. Gain an understanding of the full spectrum of triggers and actions available in FME, empowering you to enhance your workspaces for efficient automation.
We’ll kick things off by showcasing the most commonly used event-based triggers, introducing you to various automation workflows like manual triggers, schedules, directory watchers, and more. Plus, see how these elements play out in real scenarios.
Whether you’re tweaking your current setup or building from the ground up, this session will arm you with the tools and insights needed to transform your FME usage into a powerhouse of productivity. Join us to discover effective strategies that simplify complex processes, enhancing your productivity and transforming your data management practices with FME. Let’s turn complexity into clarity and make your workspaces work wonders!
Code reviews are vital for ensuring good code quality. They serve as one of our last lines of defense against bugs and subpar code reaching production.
Yet, they often turn into annoying tasks riddled with frustration, hostility, unclear feedback and lack of standards. How can we improve this crucial process?
In this session we will cover:
- The Art of Effective Code Reviews
- Streamlining the Review Process
- Elevating Reviews with Automated Tools
By the end of this presentation, you'll have the knowledge on how to organize and improve your code review proces
In 2015, I used to write extensions for Joomla, WordPress, phpBB3, etc and I ...Juraj Vysvader
In 2015, I used to write extensions for Joomla, WordPress, phpBB3, etc and I didn't get rich from it but it did have 63K downloads (powered possible tens of thousands of websites).
We describe the deployment and use of Globus Compute for remote computation. This content is aimed at researchers who wish to compute on remote resources using a unified programming interface, as well as system administrators who will deploy and operate Globus Compute services on their research computing infrastructure.
AI Genie Review: World’s First Open AI WordPress Website CreatorGoogle
AI Genie Review: World’s First Open AI WordPress Website Creator
👉👉 Click Here To Get More Info 👇👇
https://sumonreview.com/ai-genie-review
AI Genie Review: Key Features
✅Creates Limitless Real-Time Unique Content, auto-publishing Posts, Pages & Images directly from Chat GPT & Open AI on WordPress in any Niche
✅First & Only Google Bard Approved Software That Publishes 100% Original, SEO Friendly Content using Open AI
✅Publish Automated Posts and Pages using AI Genie directly on Your website
✅50 DFY Websites Included Without Adding Any Images, Content Or Doing Anything Yourself
✅Integrated Chat GPT Bot gives Instant Answers on Your Website to Visitors
✅Just Enter the title, and your Content for Pages and Posts will be ready on your website
✅Automatically insert visually appealing images into posts based on keywords and titles.
✅Choose the temperature of the content and control its randomness.
✅Control the length of the content to be generated.
✅Never Worry About Paying Huge Money Monthly To Top Content Creation Platforms
✅100% Easy-to-Use, Newbie-Friendly Technology
✅30-Days Money-Back Guarantee
See My Other Reviews Article:
(1) TubeTrivia AI Review: https://sumonreview.com/tubetrivia-ai-review
(2) SocioWave Review: https://sumonreview.com/sociowave-review
(3) AI Partner & Profit Review: https://sumonreview.com/ai-partner-profit-review
(4) AI Ebook Suite Review: https://sumonreview.com/ai-ebook-suite-review
#AIGenieApp #AIGenieBonus #AIGenieBonuses #AIGenieDemo #AIGenieDownload #AIGenieLegit #AIGenieLiveDemo #AIGenieOTO #AIGeniePreview #AIGenieReview #AIGenieReviewandBonus #AIGenieScamorLegit #AIGenieSoftware #AIGenieUpgrades #AIGenieUpsells #HowDoesAlGenie #HowtoBuyAIGenie #HowtoMakeMoneywithAIGenie #MakeMoneyOnline #MakeMoneywithAIGenie
Enhancing Research Orchestration Capabilities at ORNL.pdfGlobus
Cross-facility research orchestration comes with ever-changing constraints regarding the availability and suitability of various compute and data resources. In short, a flexible data and processing fabric is needed to enable the dynamic redirection of data and compute tasks throughout the lifecycle of an experiment. In this talk, we illustrate how we easily leveraged Globus services to instrument the ACE research testbed at the Oak Ridge Leadership Computing Facility with flexible data and task orchestration capabilities.
Utilocate offers a comprehensive solution for locate ticket management by automating and streamlining the entire process. By integrating with Geospatial Information Systems (GIS), it provides accurate mapping and visualization of utility locations, enhancing decision-making and reducing the risk of errors. The system's advanced data analytics tools help identify trends, predict potential issues, and optimize resource allocation, making the locate ticket management process smarter and more efficient. Additionally, automated ticket management ensures consistency and reduces human error, while real-time notifications keep all relevant personnel informed and ready to respond promptly.
The system's ability to streamline workflows and automate ticket routing significantly reduces the time taken to process each ticket, making the process faster and more efficient. Mobile access allows field technicians to update ticket information on the go, ensuring that the latest information is always available and accelerating the locate process. Overall, Utilocate not only enhances the efficiency and accuracy of locate ticket management but also improves safety by minimizing the risk of utility damage through precise and timely locates.
GraphSummit Paris - The art of the possible with Graph TechnologyNeo4j
Sudhir Hasbe, Chief Product Officer, Neo4j
Join us as we explore breakthrough innovations enabled by interconnected data and AI. Discover firsthand how organizations use relationships in data to uncover contextual insights and solve our most pressing challenges – from optimizing supply chains, detecting fraud, and improving customer experiences to accelerating drug discoveries.
Top Features to Include in Your Winzo Clone App for Business Growth (4).pptxrickgrimesss22
Discover the essential features to incorporate in your Winzo clone app to boost business growth, enhance user engagement, and drive revenue. Learn how to create a compelling gaming experience that stands out in the competitive market.
Atelier - Innover avec l’IA Générative et les graphes de connaissancesNeo4j
Atelier - Innover avec l’IA Générative et les graphes de connaissances
Allez au-delà du battage médiatique autour de l’IA et découvrez des techniques pratiques pour utiliser l’IA de manière responsable à travers les données de votre organisation. Explorez comment utiliser les graphes de connaissances pour augmenter la précision, la transparence et la capacité d’explication dans les systèmes d’IA générative. Vous partirez avec une expérience pratique combinant les relations entre les données et les LLM pour apporter du contexte spécifique à votre domaine et améliorer votre raisonnement.
Amenez votre ordinateur portable et nous vous guiderons sur la mise en place de votre propre pile d’IA générative, en vous fournissant des exemples pratiques et codés pour démarrer en quelques minutes.
Mobile App Development Company In Noida | Drona InfotechDrona Infotech
Looking for a reliable mobile app development company in Noida? Look no further than Drona Infotech. We specialize in creating customized apps for your business needs.
Visit Us For : https://www.dronainfotech.com/mobile-application-development/
Do you want Software for your Business? Visit Deuglo
Deuglo has top Software Developers in India. They are experts in software development and help design and create custom Software solutions.
Deuglo follows seven steps methods for delivering their services to their customers. They called it the Software development life cycle process (SDLC).
Requirement — Collecting the Requirements is the first Phase in the SSLC process.
Feasibility Study — after completing the requirement process they move to the design phase.
Design — in this phase, they start designing the software.
Coding — when designing is completed, the developers start coding for the software.
Testing — in this phase when the coding of the software is done the testing team will start testing.
Installation — after completion of testing, the application opens to the live server and launches!
Maintenance — after completing the software development, customers start using the software.
Quarkus Hidden and Forbidden ExtensionsMax Andersen
Quarkus has a vast extension ecosystem and is known for its subsonic and subatomic feature set. Some of these features are not as well known, and some extensions are less talked about, but that does not make them less interesting - quite the opposite.
Come join this talk to see some tips and tricks for using Quarkus and some of the lesser known features, extensions and development techniques.
2. @davidwengier
foreach (int item in listOfInts)
{
// do something with item
}
for (int i = 0; i < listOfInts.Count; i++)
{
int item = listOfInts[i];
// do something with item
}
int i = 0;
while (i < listOfInts.Count)
{
int item = listOfInts[i];
// do something with item
i++;
}
int i = 0;
again:
int item = listOfInts[i];
// do something with item
i++;
if (i < listOfInts.Count)
{
goto again;
}
IL_0024: ldloc.0
IL_0025: ldloc.1
IL_0026: callvirt instance !0 class
[mscorlib]List`1<int32>::get_Item(int32)
IL_002b: pop
IL_002c: ldloc.1
IL_002d: ldc.i4.1
IL_002e: add
IL_002f: stloc.1
IL_0030: ldloc.1
IL_0031: ldloc.0
IL_0032: callvirt instance int32 class
[mscorlib]List`1<int32>::get_Count()
IL_0037: blt.s IL_0024
What is lowering?
IL
foreach
for
while
gotogoto
while
for
foreach
3. @davidwengier
What is lowering?
“A common technique … is to have the compiler
“lower” from high-level language features to low-level
language features in the same language.”
Eric Lippert
https://ericlippert.com/2014/04/28/lowering-in-language-design-part-one/
12. @davidwengier
foreach
{
var e = values.GetEnumerator();
try
{
int m;
while (e.MoveNext())
{
m = (int)(int)e.Current;
Console.WriteLine(m);
}
}
finally
{
if (e != null && e is IDisposable)
{
((IDisposable)e).Dispose();
}
}
}
object[] v = new [] { 1, 2 };
Write(v);
void Write(object[] arr)
{
foreach (int s in arr)
{
Console.WriteLine(s);
}
}
Person[] v = new [] { Empl(),..};
Write(v);
void Write(Person[] arr)
{
foreach (Customer c in arr)
{
Handle(c);
}
}
13. @davidwengier
foreach (C# 5+)
{
var e = values.GetEnumerator();
try
{
while (e.MoveNext())
{
int m;
m = (int)(int)e.Current;
Console.WriteLine(m);
}
}
finally
{
if (e != null && e is IDisposable)
{
((IDisposable)e).Dispose();
}
}
}
16. @davidwengier
Lambdas
public class C
{
public void M()
{
ActHelper c = new ActHelper();
Action<string> act = c.act;
act(“hello”);
}
private class ActHelper
{
internal void act(string x)
{
Console.WriteLine(x);
}
}
}
17. @davidwengier
Lambdas
public class C
{
public void M()
{
if (ActHelper.Instance._act == null)
{
ActHelper.Instance._act = new Action<string>(ActHelper.Instance.act);
}
Action<string> act = ActHelper.Instance._act;
act(“hello”);
}
private sealed class ActHelper
{
public static readonly ActHelper Instance = new ActHelper();
public static Action<string> _act;
internal void act(string x)
{
Console.WriteLine(x);
}
}
}
18. @davidwengier
public class C
{
public void M()
{
Action<string> act = x => Console.WriteLine(x);
act(“Hello”);
}
}
public class C
{
public void M()
{
ActHelper c = new ActHelper();
Action<string> act = c.act;
act(“Hello”);
}
private sealed class ActHelper
{
internal void act(string x)
{
Console.WriteLine(x);
}
}
}
19. @davidwengier
public class C
{
public void M()
{
string y = “ World”;
Action<string> act = x => Console.WriteLine(x + y);
act(“Hello”);
}
}
public class C
{
public void M()
{
ActHelper c = new ActHelper();
Action<string> act = c.act;
act(“Hello”);
}
private sealed class ActHelper
{
internal void act(string x)
{
Console.WriteLine(x + y);
}
}
}
public class C
{
public void M()
{
ActHelper c = new ActHelper();
Action<string> act = c.act;
act(“Hello”);
}
private sealed class ActHelper
{
public string y;
internal void act(string x)
{
Console.WriteLine(x + y);
}
}
}
public class C
{
public void M()
{
ActHelper c = new ActHelper();
c.y = “ World”;
Action<string> act = c.act;
act(“Hello”);
}
private sealed class ActHelper
{
public string y;
internal void act(string x)
{
Console.WriteLine(x + y);
}
}
}
20. @davidwengier
public class C
{
public void M()
{
string y = “ World”;
Action<string> act = x => Console.WriteLine(x + y);
y = “ Fish”;
act(“Hello”);
}
}
public class C
{
public void M()
{
ActHelper c = new ActHelper();
c.y = “ World”;
Action<string> act = c.act;
act(“Hello”);
}
private sealed class ActHelper
{
public string y;
internal void act(string x)
{
Console.WriteLine(x + y);
}
}
}
21. @davidwengier
public class C
{
public void M()
{
string y = “ World”;
Action<string> act = x => Console.WriteLine(x + y);
y = “ Fish”;
act(“Hello”);
}
}
public class C
{
public void M()
{
ActHelper c = new ActHelper();
c.y = “ World”;
Action<string> act = c.act;
c.y = “ Fish”;
act(“Hello”);
}
private sealed class ActHelper
{
public string y;
internal void act(string x)
{
Console.WriteLine(x + y);
}
}
}
23. @davidwengier
Foreach and lambdas
List<Action> things = new List<Action>();
{
var e = values.GetEnumerator();
try
{
ActHelper c = new ActHelper();
while (e.MoveNext())
{
c.m = (int)(int)e.Current;
things.Add(new Action(c.act));
}
}
finally
{
if (e != null && e is IDisposable) ((IDisposable)e).Dispose();
}
}
24. @davidwengier
Foreach and lambdas (C# 5+)
List<Action> things = new List<Action>();
{
var e = values.GetEnumerator();
try
{
while (e.MoveNext())
{
ActHelper c = new ActHelper();
c.m = (int)(int)e.Current;
things.Add(new Action(c.act));
}
}
finally
{
if (e != null && e is IDisposable) ((IDisposable)e).Dispose();
}
}
25. @davidwengier
public class C
{
private int z;
public void M()
{
string y = “ World”;
Action<string> act = x => Console.Write(x + y + z);
act(“Hello”);
}
}
public class C
{
private int z;
public void M()
{
ActHelper c = new ActHelper();
c.y = “ World”;
c._this = this;
c.act(“Hello”);
}
private sealed class ActHelper
{
public C _this;
public string y;
internal void act(string x)
{
Console.Write(x + y + _this.z);
}
}
}
31. @davidwengier
Yield states
-2 : GetEnumerator() hasn’t been called
-1 : Running – Getting the next value
0 : Before – MoveNext() hasn’t been called
1- 4 : Suspended – Waiting for a MoveNext() call
5 : After – Finished.
36. @davidwengier
Yield states
-3 : Running – Getting the next value
-2 : GetEnumerator() hasn’t been called
-1 : Running – Getting the range enumerator
0 : Before – MoveNext() hasn’t been called
1 : Suspended (and After) – Waiting for a MoveNext() call
37. @davidwengier
Captain planet
private int _min;
public void M()
{
int max = 5;
foreach (int x in GetInts(max))
{
Console.WriteLine(x);
}
}
public IEnumerable<int> GetInts(int max)
{
yield return 1;
foreach (int x in Enumerable.Range(this._min, max).OrderBy(i => i * this._min + max))
{
yield return x;
}
}
???
Invented a language, having a language design meeting. Someone suggests “foreach”. Everyone agrees, except the guy in the corner. Lowering. He’s lazy. “why not just use a for loop”
Because I love it!
One abstraction layer deeper
Debugging
Performance
Lets look at one of those previous examples in detail.
Lets look at one of those previous examples in detail.
Simplified generic version. There are specific overloads for arrays, stirngs etc.
No type on GetEnumerator. Duck typing. Not really var, the compiler works it out, I just can’t express it. Also checks for implicit implementations and casts to IEnumerable. If necessary.
Two casts. One for item type, one for the type of the loop variable (because designed before generics, eg ArrayList). Means you can loop through objects, and ask for strings. EG ANIMATIONS!! Those casts could fail.
Disposable is optional. Compiler will work out whether to include it (and will leave off the try..finally entirely if it can
Note the brackets to introduce a new scope
This is the C# 4 and below version.
Subtle difference. Variable declaration inside while loop. This is a breaking change. Why? Answer is closures, which brings us to our next bit of lowering.
To talk about closures, I think its easiest to talk about lambdas.
This is what it logically does, however this has a problem. Without knowing what Console.WriteLine does, and depending on what is passed in, we can’t guarantee this doesn’t hold a reference to class C. So instead this is what the compiler does:
By using a new class, even if an instance is held in memory the compiler knows its as small as it can be. Obviously these method and class names would be different. In fact, compiler deliberately uses names that are invalid C#
This is _really_ what the compiler does though. Apologies for the size.. Various optimizations.
So far so good? Cool.
The other thing we can do wth lambdas and delegates is create closures.
Lets go back to our original lamba, but make a small change. This action now creates a closure over y. Now the compiler has to put y in the new class, and store a reference to it. This looks like this.
Lets go back to our original lamba, but make a small change. This action now creates a closure over y. Now the compiler has to put y in the new class, and store a reference to it. This looks like this.
So, can you see the problem? It doesn’t matter when you create the delegate, we’ve capture the variable y, not the value of the variable y. So the code uses the value of the variable y as at the time it is executed.
So, can you see the problem? It doesn’t matter when you create the delegate, we’ve capture the variable y, not the value of the variable y. So the code uses the value of the variable y as at the time it is executed.
So lets revisit our foreach loop, but now add a lambda in the middle. We’ll just collect a list of things to do later.. Call it poor mans async
Now this gets expanded as we know. I’ve highlighted the new bits.
In C# 5 however, we now move the declaration of m inside the loop, therefore we don’t have a problem.. Essentially when C# 4 came out everyone was so lambda happy that it exposed this quirk.
Why did they do it the other way first? Matches the “for” semantics, of having one loop variable that is redefined. Just that with “for” its much more obvious, because the user is writing that redefinition.
One last word on closures, is what the difference is when we close over a class level field, property, method etc. The field is not hoisted, instead the helper class has a reference to the original object. This can potentially lead to memory leaks. Solved by introducing local variables to capture the value, though does change the semantics (value capture not variable capture)
Kinda still on foreaches, lets look at the yield statement. Things get pretty tricky with this one.. So any questions before we continue?
The foreach part we know, and GetInts is still a method that returns an enumerable. The content of GetInts has been moved to a new class though, like we saw with lambdas. Lets look at that class
So, it implements a few interfaces. And mose of these things are obvious.
It captures the thread id, which we’ll see later is used for thread safety. It implements Idisposable as a just in case, and in this case doesn’t need to dispose anything. Will see more later.
Current we’ve seen before from Ienumerable, and there is a local variable to track it.
And it stores state. As you might know, or have guessed, the yield enumerator uses a state machine.
The intial state, if you remember, is -2
Here is the GetEnumerator method. This is where we do some thread checking. So if GetEnumerator() is called from the same thread, and we have our initial state, then this is the thing we use. This is what allows our class to be an enumerable, that can be returned from GetInts(), and an enumerator, that can do the enumeration. This sets the state to 0.
If something else calls GetEnumerator(), or we’re in a different state, then return a new instance with a 0 initial state.
Pretty basic state machine. Essentially its an unrolled loop, which makes sense because if you think about our yield statement, that was too. 4 states: Before (-2, 0), Running (-1), Suspended and After (positive integers)
Questions?
More realistic uses get a bit harder, so lets look at one.
This is a bit more typical, where in your method you’d be looping through something else, and yield returning. If the yield return unrolls the loop, well what happens when you put a loop in your loop unrolling?
Lets look at the differences.
A new Enumerator field, called wrap. In Dispose we call Finally, and that disposes of the wrapped enumerator.
The weird empty try..finally block, I cannot explain!. Could be a decompilation problem.
Just to save space on the next slide, MoveNext has nothing new that’s interesting.. Just a dispose call in a catch
Hopefully still big enough.. This looks very different! But its still a state machine. Initial state is 0, so first we set state to -3 (another type of “Running” - about get next), and get a reference to the range enumerator. Then we call MoveNext, set state to 1. Each call to this MoveNext calls the wrapped MoveNext, until we run out. At the end we call Finally() again. -1 is running the GetEnumerator, -3 is running the MoveNext
This instance doesn’t really have an “After” because it doesn’t know when to stop on its own, it simply passes calls on to the wrapped enumerator, and hence relies on that enumerators After state.
And of course you can combine these things, by having multiple yield returns, the iterator can close over variables, and fields, and can include a lambda that does the same!
This is why lowering is good. No need to implement all of this lot in IL. We know this bit will become a class, closing over some things.. And this…
At the end it will just be classes with straight forward code, containing pretty much just gotos