►
From YouTube: GitHub Quick Reviews
Description
Powered by Restream https://restream.io/
A
B
I'm
going
to
assume
that
folks
need
a
refresher
course
in
string
format
and
string
interpolation
just
to
bring
everyone
up
to
speed.
So
we'll
take
like
three
minutes
to
do
that
and
then
we'll
go
ahead
with
the
proposal
just
to
make
sure
we're
all
level
set.
So.
B
A
Can
you
hit
control
plus
a
couple
times.
B
Thank
you,
yep,
perfect,
all
right.
So,
since
the
beginning
of
net,
there
has
been
string,
format
and
string
builder
dot,
append
format
which
take
a
string
that
has
quote
holes
in
it.
So
you
can
write
hello,
open,
brace,
zero,
close
brace
as
your
string
and
then
pass
as
an
argument,
say
name
and
the
string,
format
or
stringbuilder.append
format
will
substitute
in
when
it
sees
that
brace
zero
of
closed
brace
it'll
substitute
in
the
zero
with
arguments.
B
So
you'll
get
the
output
string
of
hello
and
whatever
the
name
was,
and
you
can
have
any
number
of
these
holes.
They're
index
zero,
one
two
three:
four
that
align
with
the
zero
one.
Two
three
four
argument,
and
you
can
also
have
other
things
in
the
holes
that
kind
of
qualify
how
that
that
what
substitute
in
there
is
supposed
to
be
formatted.
B
So,
for
example,
you
can
say
zero,
colon
x2
and
that
x2
as
a
string
will
be
passed
to
the
arguments
tostring
method,
if
it
implements
the
appropriate
one,
and
that
gives
it
sort
of
details
about
how
it
should
format
itself.
So
if
that
x2
is
passed
to
an
into
32,
that
tells
it
to
format
itself
as
a
hexadecimal
value
with
two
digits,
and
there
are
all
these
standard
and
customized
format
strings
that
are,
you
know
you
can
read
very,
very
detailed
documents
on
msdn
or
docs.microsoft.com
that
describe
all
how
this
formatting
works.
B
You
can
also
say
you
know,
brace
zero,
comma
and
then
have
a
value
like
three
which
says
that
you
want
the
formatting
to
take
up
at
least
three
characters
worth
of
space.
If
it
takes
that
or
more
great,
nothing
else
is
done
if
it
takes
less
than
that,
then
the
implementation
pads
it
to
at
least
that
number
of
characters
and
then
whether
it's
positive
or
negative,
indicates
the
justification.
B
So
if
it
was
zero,
comma
three,
that
means
we
need
at
least
three
characters,
and
if
the
formatted
data
takes
less
than
that,
the
data
should
be
right,
justified
or
if
it
was
zero,
comma
negative.
Three.
If
it
was
less
than
three,
then
it
would
be
left
justified.
B
So
this
has
existed
for
a
long
time
and
then
in
c
sharp
six.
It
was
recognized.
This
is
so
popular
that
we
need
a
better
syntax
for
enabling
developers
to
express
this.
So
a
c-sharp
six
introduced
the
ability
to
put
a
dollar
sign
before
your
string
and
then
rather
than
having
brace,
zero
and
brace
one
and
then
common
name
comma
year
in
a
string
format.
B
Call
you
can
just
write
it
like
this
and
just
put
the
c
sharp
expression
directly
into
the
whole
and
the
compiler
will
generate
the
equivalent
result
as
if
you
had
written
string,
dot
format,
hello,
zero.
The
year
is
one
comma
name
comma
year
and
in
a
nutshell,
that's
what
c
sharp
interpolation
in
c
sharp
six
provided
now.
The
compiler
has
actually
lots
of
different
ways
that
it
can
lower
this
to
the
actual
code.
That's
emitted
into
your
assembly,
for
example.
B
If,
rather
than
using
name
here,
I
had
just
used
constant
strings,
then
the
compiler
is
free
to
say
I
don't
actually
have
to
do
anything
at
runtime.
I
can
do
this
entire
processing
at
compile
time
and
just
emit
a
constant
string
which
is
really
nice
or
if
I
had
string
variables
here-
and
I
wrote
hello
first
name
last
name.
How
are
you
the
compiler,
can
recognize
all
right?
Well,
I'm
only
dealing
with
string
inputs,
I've
got
hello,
comma
space
and
then
first
name
and
then
a
space
and
then
a
last
name
and
then
dot.
B
How
are
you
so?
We
could
just
emit
that
as
a
string,
dot,
concat
call
creating
an
array
of
strings
to
be
passed
in
and
if
you
had
few
two
three
or
four
strings,
then
you're
getting
about
as
good
performance
as
you
could
possibly
get
because
string
can
count
is
just
going
to
sum.
The
lengths
output
create
a
new
string
and
then
copy.
B
You
know
blit
the
input
strings
directly
into
the
output,
but
short
of
some
special
cases
like
that.
When
you
write
hello
name,
this
is
year
your
the
compiler
is
generating
for
you,
a
string
format
call
and
so
it's
generating
for
you
exactly
what
you
would
have
gotten
had
you
just
written
it
out
manually
now.
This
is
really
nice
from
a
convenience
perspective
and
interpolated
strings
get
a
ton
of
use.
B
However,
there
are
deficiencies
both
from
a
functionality
and
from
a
performance
perspective,
so
we'll
take
the
perspective
first.
First,
every
time
we
call
stream
format,
this
needs
to
be
re-parsed.
So
if
you
look
at
the
string
format,
implementation,
basically
it
takes
the
string
and
it
starts
walking.
It
copying
the
data
into
its
output
buffers
and
then,
when
it
gets
to
a
hole
it
has
to
parse
out
this
thing.
B
It
figures
out
which
argument
corresponds
to
that
it
calls
tostring
or
whatever,
on
the
thing
copies
that
over
and
then
continues
parsing
and
copying
the
the
data,
so
that
that's
a
cost
that
you
have
to
pay
at
run
time
now
there
have
been
some
proposals
around
shipping
new
types
that
enable
that
to
be
done
once,
which
is
something
we
can
look
at
for
the
future,
but
even
if
you
do
it
once
you're
still
paying
for
it
the
first
time,
whereas
it'd
be
really
nice.
B
If
all
that
parsing
could
be
done
purely
at
compile
time
since
the
compiler's
already
having
to
do
it
a
compile
time
to
do
this
translation
and
then
pay
nothing
for
that
parsing
at
runtime,
you
know
then
you'll
notice
as
another
cost
there.
B
These
casts
to
object.
So
if
it's
a
reference
type
like
string,
well
you're
not
losing
a
whole
lot,
because
it's
already
a
reference
type.
But
if
it's
year,
like
you,
know
this
this
interior.
Well,
then
it
needs
to
be
boxed
and
string
format
only
deals
with
objects
so
that
it
can
take
as
as
many
things
as
it
as
it
possibly
can
not
everything
we'll
get
to
that
annulment.
But
almost
everything.
Now
there
are
a
variety
of
downsides
to
that
boxing.
B
One
is
we're
paying
for
an
allocation
for
every
value
type
that
we
end
up,
passing
in,
but
the
other
in
the
actual
implementation,
because
everything
is
in
terms
of
object.
When
I
call
tostring
on
that,
it's
making
a
virtual
call-
or
if
I
check
to
see
if
it
implements
I
formattable
and
then
I
try
and
call
to
iformatible.2string
we're
doing
interface
checks
and
we're
doing
interface
dispatch
for
all
those
operations.
B
Whereas
if
I
was
actually
dealing
directly
with
the
value
type,
those
interface
checks
would
evaporate
at
jit
time,
because
the
jit
can
see
for
a
value
type,
whether
it
implements
the
interface
or
not,
and
those
interface
calls
could
be
de-virtualized,
because
the
jit
can
see
exactly
what
the
target
is
and
potentially
even
inlined,
avoiding
the
call
cost
plus
when
it's
inlined.
B
There
are
then
potential
knock-on
effects
where
the
call
data
from
the
call
site
can
help
optimize
the
the
in-line
invocation
so
there's
a
whole
bunch
of
benefits
there
that
we
lose
out
on
and
then
on
top
of
that,
if
we
were
passing
in
a
string,
format
has
an
overload
that
takes
one
argument,
an
overload
that
takes
two
arguments,
an
overload
that
takes
three
arguments
and
then
there's
a
final
overload.
B
That
takes
a
params
array
to
support
more
than
three
arguments,
and
if
you
end
up
having
more
than
you
know
more
than
three
holes
more
than
three
arguments,
we
end
up
allocating
a
params
array
to
to
pass
all
that
in
the
so.
Those
are
kind
of
you
know
the
the
primary
impactful
things
here
from
a
performance
perspective,
but
there's
also
a
functional
gap,
and
that
is
you
know.
We,
the
only
things
we
can
pass
here
are
things
that
can
be
boxed
that
are
either
reference.
B
Types
can
be
boxed
to
object,
which
is
almost
everything
except
there's,
this
critically
important
type,
that's
been
up
and
coming
over
the
last
few
years,
and
that
is
span
and
especially
with
being
able
to
slice
strings
as
read-only
spans
of
chars.
You
really
want
to
be
able
to
put
those
into
these
holes.
You
want
to
be
able
to
say
hello,
main
dot
as
span
3,
comma
7
or
whatever,
and
and
be
able
to
use
that.
B
But
you
can't,
because
string
format
doesn't
have
the
ability
to
pass
spans
and
as
arguments
now,
there
have
been
other
proposals
about
what,
if
we
added
overloads
for
format
that
took
generics.
So
you
know,
although
that
took
a
t1
and
overload
that
took
a
t1,
comma,
t2
and
so
on.
There
are
certainly
benefits
to
doing
that.
B
There
are
also
some
disadvantages
to
doing
that,
namely
around
generic
kind
of
explosion
and
code
size,
but
even
if
we
did
that,
we
still
couldn't
pass
read-only
spans
today,
because
you
can't
pass
a
span
as
a
generic
and
we
won't
be
able
to
until
some
future
where
we
have
ref-struct
constraints
on
generics.
B
So
we're
kind
of
stuck
in
this
place
today,
where
the
the
potential
lowering
targets
for
string
interpolation
are
both
inefficient
compared
to
what
we
would
like
and
less
functional
than
we
would
like,
and
then
on
top
of
that,
there
are
additional
costs.
When
you
try
and
do
additional
things
with
this.
B
So
you,
rather
than
storing
this
to
string
result,
I
could
have
stored
it
into
a
formattable
string
result
which
would
have
resulted
in
the
compiler
doing
the
parsing,
giving
me
the
string
and
then
an
array
of
two
arguments,
one
for
name
and
one
for
year,
and
then
I
can
pass
that
formattable
string
to
something
that
would
do
complex
processing.
For
example.
B
If
I
wanted
to
specify
an
I
format
provider
or
we
expose
formattablestring.invariant,
which
uses
cultureinfo.invariant
to
actually
do
the
formatting,
so
that
makes
that
opens
up
some
additional
possibilities
for
what
you
can
do
with
this
stuff,
but
at
yet
additional
cost
around
the
allocation
of
that
formattable
string
and
everything
getting
you
know
everything
results
in
an
array
and
so
on.
So
all
of
that
stuff
that
I
just
described
is
what
this
proposal
is
addressing.
This
is
the
api
half
of
of
the
support
that
the
compiler
is
already
already
has
in
flight
for
c-sharp
10.
B
and
I've
split
this
into
two
proposals.
This
first
proposal
is
purely
around
the
necessary
api
support
when
we're
targeting
strings.
So,
basically,
when
you
recompile,
with
csharp10
and.net,
six
and
you're
using
interpolated
strings,
you'll,
just
end
up
getting
different,
il
generated
by
the
compiler
and
more
efficient
il
and
oh
yeah.
B
You
can
also
use
read-only
spans
in
your
holes
and
then
the
second
proposal
ends
up
being
taking
advantage
of
the
fact
that
the
c-sharp
10
sport
actually
goes
above
and
beyond,
just
being
able
to
store
into
strings,
there's
actually
a
pattern
that
we
can
use
elsewhere
across
the
core
libraries
to
be
able
to
take
advantage
of
the
syntax
to
do
other,
really
cool
things.
And
so
that's
what
the
second
proposal
is
about
in
the
second
half
of
this
meeting,
hopefully
okay.
B
So
that
is
the
introductory
any
questions
so
far
on
background
or
everyone
that
was
just
you
know.
Everyone
already
knew
all
that
api
approved
great
ship
it
okay.
So
the
general
idea
here
before
we
get
into
the
api
is
that
when
now,
when
I
we're
giving
the
compiler
an
additional
way
that
it
can
choose
to
lower
a
string
interpolation,
it
can
still
choose
to
use
any
of
the
existing
mechanisms
it
has,
but
it
can
also
use
the
new
one
and
the
new
one
is
basically
given
a
string
like
a
string.
B
Interpolation
like
this,
the
compiler
can
now
generate
a
call
to
our
builder.
So
this
is
a
builder
pattern,
passing
in
some
information
that
it
gleans
from
the
call
site.
In
this
case,
it's
saying
there
are
23
characters
that
make
up
the
base
string,
so
hello,
comma
space
period
through
this
and
period
if
I've
counted
correctly,
it's
23.
and
then
the
second
is
that
there
are
two
holes.
B
One
two-
and
this
provides
this-
enables
a
builder
like
this
interpolated
string
builder,
to
make
a
guess
as
to
how
much
space
it
might
need
ahead
of
time,
for
example,
string.format
today
and
string
a
string,
dot
format
today
is
basically
does
the
number
of
characters
in
the
base
string
plus
and
it
guesses
eight
characters
per
hole.
So
it
would
be,
you
know:
23
plus
waving
my
hands
a
little
bit
two
times
eight,
so
that
creates
a
builder
and
then
for
every
part
of
this
string.
B
If
for
the
for
the
portions
of
the
base
string,
it
makes
a
call
to
this
tri-format
based
string
method
and
then
for
every
hole.
It
calls
try
format
interpolation
whole.
So
it
does
one
call
for
each
of
those
portions
and
then
at
the
end
we
get
a
two
string
call
that
produces
the
result.
B
Now
there
are
a
variety
of
things
here
that
we
have
some
say
in
and
we'll
walk
through
that
as
part
of
the
proposal,
but
as
we'll
become
more
clear
when
we
look
at
the
second
part
here,
any
decisions
we
make
around
the
shape
of
this
api
impact
every
impact,
the
pattern.
So
if
we
decide
we
don't
like
the
name,
tri
format
base
string,
we
want
to
call
it
fubar.
Every
implementation
of
this
pattern
will
have
to
be
called
fubar,
because
the
compiler
will
have
to
look
for
fubar,
and
so
this
is.
B
These
are
the
names
that
fred
on
the
c-sharp
team
has
proposed,
but
so
fred's
on
the
call-
and
we
can
you
know,
come
up
with
alternatives
that
we'd
like
if
we
see
fit.
B
Okay,
so
the
proposed
api,
the
first.
B
That's
a
great
question:
the
the
return
value
is
option.
It
can
be
either
void
or
bool,
and
it's
up
to
the
implementation
of
the
pattern
of
the
particular
pattern
to
decide
whether
it
wants
to
be
void
or
bool
in
the
in
the
case
of
interpolated
string
builder.
B
B
So,
for
example,
and
we'll
get
to
this
in,
you
know,
part
two,
but
if
you
were,
for
example,
formatting
into
an
existing
span
that
the
user
had
provided
to
you.
If
you
fill
up
that
span,
you
can't
grow
anymore,
and
so
you
start
returning
false.
So
when
we
get
to
that
part
of
the
proposal
that
builder
returns
a
boolean
from
all
of
its
tri-format
methods,
but
for
strings,
there
is
no
short
circuiting
you're,
always
doing
the
full
thing.
If
we
run
out
of
space,
we
grow
our
backing
buffer,
and
so
these
return
void.
B
But
we
use
the
same
name
regardless
of
whether
it's
void
or
bull
returning,
one
for
simplicity
and
two
to
avoid
weird
confusion
around
if
someone
happened
to
provide
both
a
format
based
string
and
a
try
format
based
string
for
the
same
argument,
what
is
the
compiler
going
to
do?
We
just
use
the
same
name
and
keep
things
simple.
B
There
are
other
examples
again.
You
can
get
this
as
part
of
the
second
proposal,
but
because
of
that
short
circuiting,
you
can
do
some
really
neat
things
with
with,
for
example,
if
I
had
a
login
a
logger-
and
I
took
a
builder
to
my
logger,
my
the
very
first
thing
my
logger
can
do
before
it
does.
Any
formatting
is
check
whether
logging
is
enabled
or
check
whether
the
log
level
is
appropriate
and
it
can
short-circuit
out
by
returning
false
effectively
and
avoid
any
of
the
costs.
B
B
Okay,
so
the
proposed
api
is
basically
two
things,
one
that
is
general
and
one.
That
is
the
specific
thing
in
compiler
services
that
the
compiler
targets
for
interpolated
string
builder
for
interpolated
strings.
B
We
have
pretty
much
all
the
relevant
types
in
corelib
inclu
and
it's
mostly
structs,
but
a
couple
classes
like
system.version
implements
this
and
it
basically
gives
the
type
the
ability
to,
rather
than
allocating
a
string
to
return
its
result
to
format
directly
into
a
span.
B
Part
of
this
proposal
is
making
that
type
public
and
also
making
it
derive
or
inherit
from
I
formattable,
but
this
is
all
up
for
discussion.
B
The
second
part
of
this
proposal
is
the
actual
builder
type
that
we
saw
earlier,
that
the
compiler
targets
as
part
of
the
string
interpolation,
so
there's
a
create
method
that
returns
the
builder
and
again
pretty
much
everything
you
see
here,
with
the
exception
of
two
string,
everything
you
see
here
ends
up
being
part
of
the
general
patterns,
so
anyone
can
implement
a
builder
again
we'll
get
to
this,
but
the
compiler
looks
for
a
create
method.
Here
it
is
returns.
B
The
builder
then
there's
a
tri-format
based
string
that
takes
the
string,
and
then
there
are
some
number
of
overloads
of
tri-format
interpolation
hole
that
take
the
data
to
be
formatted
and
then
optionally,
the
the
format
string
and
the
alignment
and
I've
made
some
command
decisions
here
about
which
overloads.
B
B
We
have
to
expose
this
one,
which
is
basically
would
let
us
accept
everything
that
you
can
possibly
do
with
string.format
today,
because
the
compiler
will
be
able
to
anything
that
could
use
with
string
format.
It
could
pass
as
object
value
and
then
optionally.
If
it
had
an
alignment,
it
would
pass
it
in
if
it
had
a
format
specifier,
it
would
pass
it
in.
B
B
So
at
a
minimum.
We
need
one
for
object,
but
that
doesn't
address
a
bunch
of
the
concerns
that
we
decided
earlier.
We
also
want
to
be
able
to
support
spans
spans,
can't
be
passed
as
objects,
so
we
need
a
dedicated
overload
for
spam,
and
this
is
an
example
of
where
this
pattern
becomes
very
flexible,
because
you
know
if,
in
the
future
there
was
another
type
you
wanted
to
expose
that
couldn't
be
treated
as
an
object
or
as
a
generic
or
if
we
wanted
to
special
case
something
and
have
some
super
duper
fast.
B
Optimized
path,
all
we
do
is
we
add
another
overload
and
compilations
will
start
binding
to
that
thing.
So
we
add
an
overload
for
read
only
span
of
char,
specifying
alignment
and
format
aren't
particularly
common,
especially
with
a
span
where
format
is
meaningless.
So
my
proposal
is,
we
just
have
the
base
that
just
takes
the
value,
which
is
the
common
case
and
then
at
least
be
able
to
handle
spans.
B
If
someone
does
specify
an
alignment
or
format
by
providing
the
fallback
then
to
handle,
you
know
optimizing
for
value
types
and
minimizing
code
bloat
at
the
call
site
by
not
having
to
have
the
compiler
always
emit
default
arguments,
for
you
know
the
if
we
didn't
spec,
if
we
didn't
provide
the
shorter
form
and
being
able
to
do
d
virtualization
with
value
types
and
in
lining
with
value
types
and
all
that
we
provide
the
the
set
of
four
overloads
for
a
value,
a
t
value
with
and
without
a
format
and
within
without
an
alignment.
B
Interestingly,
even
with
this,
we
still
need
this
overload,
because
there
are
certain
expressions
in
c
sharp
that
can't
be
target
typed
to
t
the
compiler.
Just
can't
do
it
today
may
not
be
able
to
do
it
in
the
future
and
having
this
object
ends
up
being
a
fallback.
B
B
Then
we
have
these
string
overloads,
which
are
relevant
for
two
reasons.
One
strings
are
super
duper
duper
common
and
we
can
actually
optimize
string
better
than
if
we
just
had
object
or
going
through
the
generic
path.
B
But
second,
because
strings
are
reference
types,
they
are
implicitly
convertible
to
object
and
because
strings
have
an
implicit
cast
to
read
only
span
char.
If
you
tried,
if
we
didn't
have
this
overload
and
you
tried
putting
in
a
whole
a
string
with
either
or
both
in
alignment
or
format,
the
compiler
would
see
these
two
overloads
as
being
ambiguous
and
it
would
fail
to
compile-
or
in
this
case
it
would
fail
to
use
this
new
mechanism,
and
it
would
silently
fall
back
to
string
that
format.
B
And
then
you
end
up
paying
all
those
other
costs
for
your
your
other
things
so
having
this
enables
us
to
avoid
that
ambiguity.
B
Now
that
ambiguity
will
still
exist
if
there's
any
other
reference
type
that
you
try
and
use
in
a
whole
that
has
an
implicit
conversion
to
a
span
of
char,
a
read,
only
span
of
char.
We
don't
have
any
other
ones
of
those.
I
think
they're,
probably
super
rare.
If
we
came
across
another
one
in
the
future,
we
could
revisit
it,
but
all
it
takes
is.
B
If
someone
you
know,
has
that
issue
they
can
cast
at
the
call
site
to
resolve
the
ambiguity
and
then,
finally,
there
are
these
four
at
the
bottom
which
I'm
proposing.
B
We
don't
do
right
now,
but
we
have
in
our
back
pocket
if
we
can,
if
we
care
to,
I
opened
an
issue
a
week
or
two
ago
that
if
you
try
and
use
a
nullable
via
one
of
these
generic
interfaces,
it
is
super
duper
slow,
like
100x
as
slow
as
anything
else,
just
because
of
the
quality
of
the
code
jen,
we
think
we
can.
We
think
we
can
fix
that
by
the
time
we
fix
dot
net
six
and
make
it
much
closer
to
t.
B
E
B
C
B
C
B
We
get
to
proposal
we'll
see
that
there
are
other
possible
builder
types,
but
this
one
is
known
to
the
compiler
such
that.
If
you
you
know,
you
don't
utter
the
there's,
nothing
here
that
specifies
the
builder
name.
So
for
this
case
the
builder
is
known
to
the
compiler,
just
as
string.format
and
string
and
cap
are
known
to
the
compiler
for
interpolated
strings
today,.
E
F
B
C
The
the
main
reason
that
I
wanted
with
such
as
with
such
a
super
specific
name
dustin,
is
to
minimize
the
really
really
minimize
the
chance
that
anyone
could
potentially
have
a
type
that
somehow
manages
to
match
this
pattern.
B
And
so
I'm
I'm
totally
fine
calling
this
tri-format
whole
or
just
try
format.
The
the
key
is.
We
need
this
differentiated
from
this
yeah.
I
understand
I
was
just
asking
the
question:
it's
mostly
for
fred,
so
we
could
call
this
try
format
base.
We
could
call
this
try
format
whole
like
we
can
come
up
with
other
options.
Why.
G
G
B
Yeah,
so
for
what
you
currently
see
on
the
screen,
they
are
not.
However,
there
are
ways
that
they
are
once
you
get
into
other
builders.
So,
for
example,
what
what
you
don't
see
here
is
that,
as
part
of
part,
two
I've
actually
there's
I'm.
B
I
propose
adding
additional
constructors
here
or
additional
create
methods
here,
one
of
which
accepts
an
I
format
provider
and
that
I
format
provider
certainly
ends
up
impacting
these
things
when
when
it
takes
a
format
for
example,
but
it
can
even
impact
this
there's
a
little
known
feature
in
string
formatting,
there's
an
interface
called,
I
custom
formatter,
which
basically
says
I
want
to
overrule
anything.
The
type
thinks
it
knows,
and
I
want
to
take
over
all
formatting,
and
so
you
ask
the
format
provider.
Do
you
provide
me
an
eye
custom
formatter?
B
If,
yes,
all
formatting
gets
redirected
through
that
thing,
you
basically
pass
in
the
value
you
pass
in
the
format
you
pass
in
the
provider
and
it
chooses
what
to
output.
So,
for
example,
you
can
use
this
to
add
your
own
custom
format
strings.
You
could
say,
in
addition
to
be
on
the
support
d
and
x
on
in
32.
I
also
want
to
support
b
like
to
output
as
binary,
for
example,
so
you
can
implement
a
custom
formatter
to
do
that.
This
value
needs
to
go
through
that
custom
formatter.
B
If
it
exists
this
one
should
not.
That
makes
sense,
but
then
there
for
other
builders.
There
are
other
things.
For
example,
if
you
were
doing
a
you
know,
a
logging
builder,
you
might
very
likely
want
to
treat
the
the
constant
portions
of
your
string
different
from
the
you
know,
substituted
portions,
or
maybe
you
had
some
kind
of
complicated
localization
logic
where
you
wanted
to
substitute
the
base
string
with
something
else,
but
keep
the
holes
the
same,
etc
so
to
make
it
more
flexible,
they
are.
They
are
separated.
B
Good
question
I'm
going
to
well,
I
can
we
talked
a
little
bit
about
it
earlier,
but
the
they
can
either
return
void
or
they
can
return
bool
as
part
of
the
general
pattern,
and
so
we,
but
we
didn't
want
to
have
two
different
names
for
the
two
different
things:
to
keep
things
simple
and
avoid
complexity
with
someone
providing
as
part
of
the
pattern,
two
overloads
for
the
same
input
but
with
diff.
B
You
know
with
different
return
types
which
you
can't
do
in
c
sharp,
but
you
could
if
they
were
called
something
different,
so
basically
they're
always
called
try,
but
they
can
optionally
return
void
or
rule,
and
in
this
case
we
never
return
true
or
false,
because
it's
always
from
the
per
from
the
point
of
view
of
the
builder.
It's
always
successful.
The
try
basically
indicates
whether
it
should
stop
formatting
because
it
runs
out
of
room
or
something.
B
But
this
interpolated
string
builder
is
just
going
to
grow
its
backing
buffer,
whereas
you
will
have
other
builders
that
will
see
which
do
want
a
short
circuit
and
say
for
some
reason.
I
can't
format.
Stop
the
whole
operation
and
providing
a
bool
allows
the
compiler
to
then
short
circuit
out
we'll
see
an
example
of
that
in
the
second
part,.
A
B
A
A
Right
I
mean
we've
had
things
like
you
know,
you
could
have
a
you
know,
bounded
collection
and
you
have
a
append
that
returned
a
boolean
saying,
I'm
sorry.
I
was
already
full
like
we've
we've
had
we
have
non-tri-booleans,
I
just
don't
think
we
want
non-boolean
tries
okay,
I
I'm
I'm
again
totally
fine
with
that.
Yeah
other
notes
that
I've
already
taken
down
here.
So
I
see
that
this
is
a
ref
struct.
Is
that
important.
B
Yes,
for
a
couple
reasons,
one
is
just
an
implementation
detail.
We
use
span
internally
to
keep
things
simpler.
Obviously
we
wouldn't
have
to
do
that.
The
second
is
one
thing
you
don't
see
here
is
as
part
of
the
second
part
of
the
proposal.
There's
another
create
overload
here
that
allows
you
to
pass
in
scratch
space
and
it
does
so
as
a
span,
so
it
could
be
stack
space
if
you
wanted
to
and
then
related
to
that
is,
I
would
really
like
it.
B
It's
unlikely
to
happen
for
c
sharp,
ten
and
dot
net
six,
but
I
would
really
like
it
if,
in
some
future
version
of
c
sharp,
maybe
c
sharp,
eleven
or
whatever
the
compiler
could
actually
pass
in
some
scratch
space
that
itself
created,
and
so
by
making
this
a
refstruct.
Now
we
we
make
that
basically
still
possible
for
the
future.
Now
we
could
always
say
in
some
hypothetical
future
like
that
we
introduced
yet
another
version
of
this
builder.
That
is
not
a
that
is
a
restructuring.
B
This
one
isn't
but
there's
very
little
downside
to
just
making
it
a
restaurant
today.
On
top
of
that,
there's
some
minor
benefits
around
you
know
as
a
refstruct.
We
know
it
can't
be
stored
on
the
heap,
and
so
if
someone
was
creating
one
of
these
things
directly,
we
don't
have
to
worry.
We
have
to
worry
a
little
bit
less
around.
You
know
any
array
pool
back
state.
B
That's
in
one
of
these
things
becoming
an
issue
because
it
was
stashed
for
some
longer
lifetime
or
whatever,
but
it's
basically,
you
know
a
lot
of
little
things
that
add
up
to
it
being
a
rep
struck,
rather
than
one
critical
reason.
A
Yeah,
speaking
of
you
know
that
you
can't
go
to
the
heap.
Can
someone
remind
me
what
happens
inside
state
machine
methods
with
regards
to
span?
Is
it
just?
They
can't
cross
an
await
or
a
yield
boundary.
B
So
today
you
can't
use
a
weights
at
all.
Sorry,
you
can't
use
spans
at
all
inside
of
an
async
method.
That
is
a
compiler
enforced
limitation.
The
actual
limitation
would
be
that
you
couldn't
use
an
await
across
sorry.
You
couldn't
use
a
span
across
and
a
weight
boundary.
There
is
whether,
whatever
the
compiler
chooses
to
do
here,
there's
no
functional
reason
why
the
compiler
couldn't
support,
awaits
in
holes
with
the
string
interpolation.
B
Now
it's
possible
it
would
choose
not
to
for
fred's
sanity,
but
there's
no
fun,
there's
no
functional
reason.
It
couldn't
right!
Well,.
B
C
So
so
to
be
clear,
the
way
that
the
way
that
it's
spec'd
right
now
in
the
way
that
is
currently
implemented,
we
don't
do
any
evaluation
up
front.
So
what
this
means
is
that
user
code
is
actually
running
at
the
at
the
tri-format.
Interpolation
hold
call
right,
so
if
they
have
a
if
they
have
an
await
in
there,
it
actually
runs
at
that
point,
and
so
the
way
it's
implemented
currently
is
that
the
builder
is
basically
just
going
to
say
if
there's
an
await
inside
the
hole
fall
back
to
string.format
or
string.concat.
C
We
could
for
for
this
particular
case
or
general
cases
that
involve
void
returning
methods.
We
could
evaluate
things
up
front
and
allow
you
to
use
async
weight
in
the
holes
right.
We
could
do
that,
but
that
is
not
the
way
that
is
implemented
currently.
A
Call
so
so,
just
as
a
user
experience
you,
we
can
show
this
shiny,
new
thing
and
say:
hey
look.
You
can
use
read-only
spans
now,
but
not
if
you're
in
a
a
yield,
return,
iterator
or
an
async
method,
because
it's
going
to
fall
back
to
string.format
which
could
handle
it.
C
You
so
yield
return,
iterators
can
use
spans.
Just
fine
yield
is
a
yield
return
is,
is
it's
not
an
expression
right,
so
you
can't
use
that
inside
of
a
string
anyway
and
and
then
in
terms
of
async
await
you
couldn't
be
using
it.
You
can't
be
manually
using
a
span
there
anyway
right
so.
B
B
If,
if
one
of
your
arguments
was
a
read-only
span,
and
another
of
your
arguments
was
await,
something
which
would
be
incredibly
strange
combination
sure,
especially
because
today,
that
would
only
be
possible
if
that
thing
that
was
a
span
was
a
method
returning
a
property
or
a
method
returning
a
span,
because
you
can't
actually
declare
one
in
an
async
method
today,
then
that
would
end
up
failing
to
compile,
because
it
would
try
and
fall
back
to
string
format,
and
you
couldn't
use
the
span
there,
but
you're
no
worse
off
than
you
are
today
and
if
we
wanted
to
the
compiler
can
address
that
by
doing
the
for,
for
this
case,
for
doing
the
computation
of
these
ahead
of
time,
just
as
it
does
today,
where
you
yourself
can
work
around
it
by
doing
that
right
or
you
yourself
can
work
around
it.
A
A
A
B
D
B
C
Well,
I
think
it
was
in
general
talking
about
like
other
builder
types.
Oh.
C
So
so
the
thing
about
other
builder
types
also
is
that
we
haven't
yet
settled
whether
on
whether
or
not
we're
actually
going
to
allow
refstructs
in
the
general
in
in
the
general
pattern
case,
because
there
are,
there
are
a
number
of
other
concerns
there.
A
B
C
The
problem
is
attempting
to
do
this
without
that
support,
yeah
and
then
the
other
thing
here
steve
do
you
want
to
bring
up-
or
at
least
I
would
like
us
to
bring
up,
is
dyspos
and.
A
A
B
Yeah,
so
let
me
take
that
in
two
parts
so
I'll
take
the
latter
part
first.
So
when
t
is
a
value
type
so
inside
these
object
string-
and
you
know
t
here
actually
just
object
in
t-
we
will
check
to
see
whether
the
the
value
implements
I
formattable
and
I
span
formattable.
B
B
Calls
for
things
like
in
32.try
format
via
the
constrained
call
of
the
interface
get
inlined,
it's
very
very
nice.
The
only
time
you
end
up
paying
for
the
interface
call
is
on
the
object
and
you
would
pay
for
that,
even
if
we
went
through
a
generic
to
do
it,
because
if
it's
a
reference
type
you're
getting
a
shared
generic
implementation,
not
something
specialized
to
that
t.
So
from
that
perspective
you
don't
you
don't
lose
a
whole
lot
there.
B
I
did
experiment
with
a
different
set
of
overloads
where
these
were
t
constrained
to
struct,
and
then
I
had
a
full
set
of
object,
overloads
for
for
handling
all
value
types,
the
idea
being
that
we
don't
get
any
benefit
from
sending
reference
types
through
the
generic
code.
In
fact,
it
has
a
little
bit
of
expense.
B
So
why
not
just
let
reference
types
use
the
object
code
path,
the
problem
with
that
is,
if
you
have
a
t
that
is
a
value
type
and
it's
not
constrained
to
struct,
then
that
ends
up
going
down
this
path
and
it
gets
boxed
and
all
that
bad
stuff
happens,
and
it's
very
common
to
have
t's
that
are
value
types
that
aren't
constrained
to
struct.
B
We
also
can't
have
the
exact
same
overload,
one
where
t
is
constrained
to
struct
and
one
where
t
is
constrained
to
class.
Doesn't
not
that's
not
supported,
so
we
kind
of
you
know.
This
is
basically
the
best
set
of
overloads
I
I
could
come
up
with,
and
it
and
the
you
don't
pay
the
interface
costs
on
one
of
the
most
common.
B
H
B
We
can
do
that
or
we
can
go
through
the
issues
for
discussion,
the
first
of
which
is
the
method
names.
So
again,
we
can
start
with
that.
If
you
want.
A
Okay
yeah,
so
you
know,
I've
already
said
my
part
about
the
try.
A
If
the
purpose
of
the
base
string,
which
feels
like
a
terrible
name,
is
that
it
won't
ever
be
formatted,
then
format
feels
like
the
wrong
word
and
it
feels
like
it's
just
a
pinned
or
append
fixed
string
or
or
something
yeah.
I
agree
with
that.
A
Okay,
like
we
really
don't
want
the
word
format
in
it,
because
it's
explicitly
not
going
through
the
format.
Oh
that
reminds
me
for
a
meta
concept.
Is
anything
in
this
new
proposal
going
to
fix
where
interpolated
strings
and
localization
are?
Let's
call
them,
not
friends,
instead
of
enemies,
because
enemies
is
a
bit
strong.
B
No,
I
assume
you
mean
localization
becomes
because
the
string
is
coming
from
a
resource
file
or
something
like
that,
and
so
it's
not
known
at
compile
time.
No.
This
does
not
address
that.
There's
a
separate
issue
that
martin
proposed,
which
is
basically
let's,
do
all
the
pre-computation
at
basically
startup
time
or
first
access,
so
that
you
can
pass
in
something
from
a
resource
file
and
then
use
generics,
t1,
t2,
t3,
etc.
Certainly
something
we
can
look
at
separately,
but
not
as
part
of
this
okay.
E
E
B
A
This
is
the
base
dustin,
since
you
already
knew
what
the
spec
words
were.
What
does
the
spec
call
the
thing?
That's
not
the
thing
that
you
called
an
interpolation.
B
F
B
F
Piece,
I
think
it's
I
I
I
think
it's
actually
kind
of
weird,
if
I
recall,
and
I'm
not
certain
okay
and
there's
these
are
tokenized
very
strangely
to
try
and
keep
it
context-free
and
they
have
to
do
with
like
prefixes
and
post-fixes
and
weird
things.
I
I
don't
recall
fred,
do
you
recall
cleaning
it
up
right
now,
yeah,
it's
it's
very
weird,
just
because
tokenizing
these
things
is
awkward
because.
F
A
Seems
more
reasonable,
I
mean
that's
kind
of
what
it
is.
K
And
there's
the
reason
they're
different
is
because
the
base
string
here
does
not
go
through
any
formatting
ever
and
so
it's
not
equivalent
to
say
putting
an
interpolation
hole
that
has
the
string
literal
of
the
same
value
in
it
correct
right
this,
and
this
are
different.
C
I
think
that's
probably
fine.
Okay,.
C
C
The
actually,
the
only
thing,
I
wonder
about
append
format,
append
and
append
format,
and
this
may
be
good.
This
may
be
bad,
but
it
does
mean
that
you
know
we
could
potentially
use
if
we
exposed
the
right
static
method
on
string
builder,
we
could
actually
use
string
builder
as
a
builder
type,
because
it.
G
E
Yeah,
I
guess
that
goes
back
to
the
other
question
which
I
guess
stephen
wants
to
talk
about
later,
which
is,
I
guess,
using
different
builders
yeah
yeah.
So
maybe
we
just
postpone
that
then
and
revisit
the
naming.
If
we
can
actually
talk
about
the
whatever
accessibility
mechanism
sure
so.
B
A
A
Like
because
the
format
is
not
a
requirement
for
these
holes,
especially
if
you
have
the
universal
formatter
sure
append
and
a
pen
formatted,
that
sounds
funny.
Yep.
F
F
E
B
C
B
Okay,
there
are
two
categories
of
types
that
can't
be
boxed
or
generics.
Today
we
already
talked
about
spans,
ref
strucks.
The
other
is
pointers.
I
don't
think
we
should
add
overloads
for
pointers.
Someone
could
always
cast
to
an
end
pointer
and
then
things
just
work,
but
I
wanted
to
call
out
here
in
case
anyone
felt
differently.
K
I
think
that's
fine
is
probably
the
highest
user
of
pointers
in
this
meeting.
I'm
used
to
having
to
cast
pointers
to
inuint
just
to
get
them
to
work
with
interpolation
or
formatting,
or
basically
anywhere,
that
takes
a
generic
type
and
particularly
since
inning
and
inuit
were
supported.
We
now
have
the
overloads
that
allow
you
to
customize
that
formatting
to
be
hexadecimal
or
general
etc.
So
people
should
be
able
to
do
whatever
they
need
to
here.
H
E
B
Since
the
compiler
gets
to
choose
what
mechanism
it
uses
it
can
choose
if
it
can't
do
it
with
the
builder
it'll
fall
back
to
string,
concat
or
string
format
if
it
could
use
one
of
those
more
generally.
If
it
was
for
the
builder
pattern
and
you-
and
there
was
just
no
way
it
could
compile,
it
will
fail
to
compile.
A
And
is
that
basically
it's
gonna,
like
ghost
compile
or
shadow
compile,
and
if,
as
soon
as
it
sees
it
can't
fit,
then
it's
going
to
fall
back
to
string.format
or
like
if
I
made
a
cust,
if
I
made
a
custom
one,
I
know
we're
not
there
yet
and
for
some
reason
it
didn't
take
strings.
It
only
supported
the
the
literal
and
and
numeric
types.
Is
it
going
to
see
that
and
drop
back
to
string.format,
or
is
it
going
to
just
fail
to
compile
because
I
passed
in
a
string?
It's.
C
And
that
will
somewhat
depend
on
the
other
overloads
of
that
method.
So
like
say
you
have
when
I
say
that
method
I
mean
the
method
you're
passing
the
interpolated
string.
To
so
say
you
have
like
a
log
information
or
whatever
method,
you
know,
and
you
call
and
you
have
a
version
that
takes
a
string
and
you
have
a
version
that
takes
a
builder
if
it
does.
If
this
interpolated
string
is
not
convertible
to
that
builder
type.
C
For
whatever
reason-
and
it
is
convertible
to
the
string,
it
will
pick
the
string
because
it
is
a
string
right
and
then
and
if
you
in
and
then
the
likelihood
is
it's
not
going
in
in
this
weird
case
that
you
that
you've
posted
where
your
builder
doesn't
support,
string
strings
in
the
whole.
Then
then
it
would
compile.
But
most
cases
like
that
are
going
to
be
things
that
involve
pointers
and
it
just
straight
up,
won't
compile
ever.
A
Right,
okay,
so
it's
not
once
it
sees
wait.
I
couldn't
resolve
a
call
to
a
pinned.
Formatted
crap,
try
just
going
the
string.format
route
it
at
that
point.
It's
already
committed.
It's
decided
it
was
calling
a
pin
formatted
and
then
it
failed
yeah.
Okay,
I'm
just
trying.
A
E
The
only
thing
I
would
be
careful
with
if
it's
common,
if
there
are
common
cases
where
certain
data
types
would
fall
back
to
the
old
thing
that
might
become
a
performance
trap,
then
right
because,
oh
you
just
you
know
edit
this
one
more
point
of
view
and
then
suddenly
the
whole
thing
goes
to
some
slow
cool
pad.
That
will
be
unfortunate,
but
if
pointers
don't
compile,
I
think
that's
fine,
then
we
can
edit
when
somebody's
asking
for
it.
C
Yeah,
the
the
things
that's,
the
overloads
that
steve
has
added
should
be
should
be
enough
to
get
all
the
things
that
work
in
string
interpolation
today
and
the
and
that's
one
of
the
we
went
back
and
forth
several
times
over
that
object
overload,
because
today,
for
example,
you
can
put
a
new
right.
You
can,
you
can
say,
open
bracket,
new
open,
paren,
close
paren,
close
bracket
and
that
works
today,
because
string.format
takes
an
object
and
so
that
new
can
be
target
typed
to
an
object.
A
Yeah,
so
just
so,
I
can
load
it
in
my
model
of
the
universe
before
fred
gets
to
laugh
at
me
again,
because
my
brain
falls
back
to
c
sharp.
Six
is
the
last
version
that
we
shipped.
When
will
this?
When
will
it
fall
back
to
string.format,
like
what
kind
of
things
could
someone
do
with
the
thing
as
currently
spec
implemented?
That
will
cause
it
to
bail
on
this
and
go
to
string.format.
C
So
there
are
one
you're
using
something
like
pointer,
yeah,
exactly
exactly
steve
one
you're
using
something
like
pointer,
in
which
case
that
will
fail
to
compile
two
you're
using
an
await
in
the
hole
for
string
for
an
interpolated
string
literal
as
an
interpolated
string,
we're
still
discussing
whether
or
not
we
can.
We
should
just
evaluate
things
up
front
and
make
that
case
work
as
well,
and
the
other
question
is
dependent
on
whether
or
not
we
have
a
disposed
implementation
on
this
builder
type.
C
If
we
do
have
a
dispose
implementation,
then
we
can't
use
this
pattern
in
say:
can
catch
when
blocks,
because
you
can't
put
a
try
catch
or
you
can't
put
a
tri-finally
scope
inside
of
a
of
a
catch
of
a
catch.
One
block
any
any
place
that
the
seal
heart
doesn't
allow
you
to
put
a
try.
Finally,
basically,
okay.
C
Yeah,
so
the
th
that
is
because
c
sharp
doesn't
know
a
common
type
between
one
and
null
like
you,
you
can
make
the
argument.
We
should
be
able
to
infer
nullable
event
right,
but
we
don't
so
that
just
doesn't
compile
because,
but
that
that.
C
C
T
isn't
a
target
type,
it
doesn't
give
us
any
target
type
information
string.
One
can't
be
converted
to
a
string.
One
also
can't
be
converted
to
a
read-only
span
and
neither
can
null,
but
it
can
be
converted
both
of
those
can
be
converted
to
object
and
so
which
is
bind
to
object.
A
Okay,
so
really
it's
right
now,
only
only
in
a
weight
expression
that
will
be
like
stringed
up
format,
yep,
okay,
and
even
that
I
feel
like
we
can
make
that
work.
If
we
want
to
but
yeah.
K
Is
there
concern
about?
It
sounds
like
in
one
case
we
will
preemptively
evaluate
the
operands
being
passed
through
the
holes,
and
it
sounds
like
in
another
case.
We
won't
is
that
going.
C
To
be
of
concern,
no,
that
is
so.
That
is
not
how
it
works.
What
we're
discussing
four
interpolated
strings
as
strings
is
potentially
doing
that,
but
the
general
pattern,
if
you're
using
an
interpolated
string
as
one
of
these
builder
types
and
you're
taking
the
argument,
type
you're
literally
observing
the
builder
type.
That
is
not
how
it's
going
to
work.
K
Okay,
so
it
would
only
be
for
string
literals,
basically.
B
Okay,
next
topic
for
conversation
is
the
this,
so
there
are
a
variety
of
ways
we
could
expose
this
capability.
I
like
what
I
currently
have
on
the
screen,
but
I
wanted
to
discuss
it.
There
are
a
couple
other
options.
One
other
option
is
we
could
just
have
I-span
formattable
be
separate
from
my
formattable
rather
than
inheriting
it.
I
like
it
inheriting
from
it,
because
it
basically
says
my
implementation
has
two
different
ways
to
generate
the
same
data.
B
I
can
either
write
it
into
a
destination
span
or
I
can
produce
it
from
two
string
and
it
really
ties
together
the
fact
that
there
are
two
different
ways
to
generate
the
same
data
and
do
something
else
with
it,
whereas
if
it
was
two
different
implementations,
it's
not
if
one
didn't
require
the
other
they're,
not
in
my
mind
not
as
tightly
coupled
together.
There
is
a
performance
benefit
to
span.
B
I
spent
for
metal
being
derived
for
formattable,
which
is
most
reference
types
that
I
have
seen
well,
it's
true
today
that
most
reference
types
do
not
implement.
Iso
span
formatting,
and
I
think
that
will
be
continued
to
be
true
in
the
future.
They
might
implement,
I
formattable,
but
it's
less
likely
they'll
implement
this
one
by
having
this
one
derived
from
this
one.
The
implementation
can
first
test
for,
is
I
formattable
and
if
it's
not
is
if
it's
not,
I
formattable,
which
is
definitely
the
most
common
case
for
reference
types.
B
Then
we
don't
also
have
to
check
for
ispan
formative,
so
we
can
get
away
in
the
most
common
case
for
reference
types
by
only
doing
one
interface
check
rather
than
two,
because
we
can
first
check
for
this,
and
only
if
it
is
I
formattable,
then
we
can
also
check
for
ispan
formative
for
value
types.
It
doesn't
matter
because
they
evaporate
anyway.
B
The
other
option,
though,
is
these
are
separate,
or
we
could
consider
adding
a
default
interface
method.
We
could
add
this
as
a
default
interface
method
to
I
formattable
itself,
which
brings
up
the
dreaded
dim
word.
B
But
it's
possible!
You
really
want
to
know
whether
this
implementation,
like
the
virtual,
the
base
implementation,
is,
would
probably
just
call
tostring
and
then
would
try
and
copy
that
to
the
destination
span.
B
K
Format
and
provider
are
default.
If
I
remember
correctly.
B
K
E
E
You
know
gnarly,
potentially,
issues
with
dimms.
My
other
question
for
fred
is
like
I
suppose
none
of
this
work
will
work
for
bb
right,
so
we're
not
going
to
propose
any
changes
for
vb
to
support
these
new
overloads
that
take
builders
right
in
vb
world.
You
would
always
either
fall
back
to
the
string,
one
or
just
plain,
not
compile
right.
C
Good
question:
I'm
not
certain
the
main
issue
that
that
we
need
to
be
careful
about
is
if
we
start
adding
and
if
we
start
having
our
customers,
you
know
logging,
libraries
and
stuff
moving
to
this
to
this
world.
We
want
to
make
sure
that
bb
can
continue
to
operate
in
it
and.
G
C
F
I
mean
that's
the
the
c-sharp
interpolation
design
is
actually
based
on
what
we
decided
for
vb.
That's
how
the
dollar
got
in
there.
D
B
Okay,
we
talked
about
overloads.
We
talked
about
dynamically
checking
price
per
span
for
medical
all
right,
so
that
brings
us
to
and
we
did
this
one.
So
the
only
other
open
issue
I
had
was
dispose.
B
Fred's
favorite
topic
before
so
various
builders
have
resources
that
need
to
be
cleaned
up.
Interpolated
string
builder
may
be
wrapping
an
array
pool
array
that
it
would
really
like
to
return,
as
I
currently
have
it
implemented.
Two
string
creates
the
string
grabs.
The
array
clears
out
the
builder
and
returns
the
array
to
the
pool
and
then
returns
the
string
we
could
separate
out
just
have
two
string
literally
just
call
spam.2
string
with
the
right.
B
You
know
arguments
and
then
have
this
be
expose
a
dispose
method
that
does
the
returning
and
the
clearing,
and
if
we
did
that,
then
assuming
we
chose
to
go
this
route,
the
compiler
would
add
support
for
builders
being
disposable
and
it
would
output
any
interpolation
as
with
a
try.
Finally,
with
the
finally
blocked
calling
dispose
on
the
builder,
there
are
pros
and
cons
to
this
in
general,
but
it's
in
particular
for
this
built-in
one
for
the
on
the.
B
Let
me
do
the
cons
first,
and
the
reason
I
don't
have
it
here
right
now
is,
if
all
you're
doing,
is
this
there's
very
little
reason
to
need
to
to
pay
the
overhead
in
il
and
execution
whatever?
B
For
a
try,
finally,
the
only
reason
is
if
you
really
wanted
to
clean
up
and
return
the
array
to
the
pool,
even
in
the
case
of
you
know,
year.two
string
throwing
an
exception
today
we
don't
we,
we
use
pooled
arrays
in
string
format
today,
and
we
don't
return
them
to
the
pool
in
such
a
case
because
in
general
we
don't
pay
the
extra
costs
for
the
common
case
to
return
arrays
to
the
pool
in
exceptional
situations.
B
We
also
don't
expect
these
types
to
be
used
by
developers,
which
is
why
I'm
comfortable
having
something
in
compiler
services
that
is
a
struct,
wrap
and
a
rate
pool
array
to
begin
with,
whereas
we've
you
know
tried,
we've
refrained
from
doing
so
until
we
have
non-copyable
structs
in
sort
of
user-facing
types.
B
There
is
one
case
where
it
becomes
a
little
bit
more
relevant,
so
I'm
going
to
jump
just
to
show
a
signature
from
the
second
part
of
the
proposal.
Just
to
talk
about
this,
and
that
is,
I
would
I'm
proposing
that
we
add
an
overload
to
string.format.
B
That
takes
a
builder
and
the
way
this
would
work
is
you
can
write
this
and
waving?
My
hands
for
a
moment
this
will
work
exactly
as
you
expect
it
to
work.
This
interpolation
happens
using
this
culture.
I
just
didn't,
have
to
write
0
1
and
pass
the
x
and
the
y,
but
obviously
not.
Obviously,
the
compiler
is
generating
code,
something
like
this,
where
it's
it's
doing
the
same
kind
of
generation
that
you
saw
previously
and
then
it's
taking
the
builder,
and
it's
passing
that
builder
into
the
method.
B
Here
we
are,
the
compiler
is
generating
code
that
is
passing
around
a
struct
that
contains
a
resource
and
passing
it
into
this
this
method.
Now
again,
the
compiler
is
generating
that
code,
but
it's
possible.
Someone
could
be
writing
their
own
thing.
That
tried
to
use
this
and
would
pass
it
in,
and
then
you
kind
of
like
it
to
be
a
try.
A
B
H
H
Stack,
we
can
make
that
work
in
the
sense
that
like
if,
instead
of
taking
the
interpolated
builder,
you
took
a
a
like
in
interpolated
builder,
dot,
some
nested
type
and
then
that
nested
type
has
a
reference
back
to
the
original
source
of
truth.
That
way,
we
can
actually
manipulate
it
in
a
fully
safe
fashion.
C
The
the
thing,
the
thing
I'll
to
remind
everyone
as
well,
though,
is
that
for
these
builders,
particularly
these
builders
that
return
bulls.
This
is
not
one
that
returns
a
bool,
but
these
builders
that
do
return
to
bull
user
code
is
going
to
be
running
in
the
middle
of
this
thing,
and
so
you
know
for
this
case
for
the
for
these
cases
that
we've
shown
you
know,
they're,
probably
not
going
to
be
throwing
exceptions,
but
user
code
can
throw
any
type
of
exception
that
it
just
so
happens
to
choose
right.
C
Do
you,
let
me
ask
a
question
to
clarify
that
steve:
do
you
not
care
about
it
for
the
framework,
or
do
you
not
care
about
it
in
general,
like,
for
example,
if
someone
is
doing
a
log
method
in
the
middle
of
a
hot
loop
and
they're
continually
allocating
and
throwing
in
the
middle
of
this
in
the
middle
of
this
hot
loop?
Is
that
a
concern.
C
B
A
Yeah
yeah,
I
mean
in
in
the
case
of
this
one
argument
on
or
one
overload
of
string.format,
because
it's
not
the
pattern.
You're
tying
it
to
exactly
this
interpolated
string
builder,
saying
that
it
has
to
be
passed
by
ref,
because
it's
immutable
restructure
like
even
if
there's
something
that
doesn't
work
right
now.
I
think
we
can
make
it
work
and
it's
it's
better
than
letting
these
things
get,
because
if
we
don't,
I
guess
this
is
back
to
your
disposal.
A
If
it's,
if
the
2
string
is
doing
the
clearing,
then
the
fact
that
you
call
pass
this
in
and
called
tostring.
If
that
cleared
and
returned
to
the
array
or
returned
the
array
to
the
array
pool
now
we're
really
setting
ourselves
up
for
we're
letting
these
things
go
past
method
boundaries.
This
is
going
to
be
double
return.
So
now
it's
not
allowed
to
use
the
array
pool.
So
now,
there's
no
point
in
the
type
having
been
a
rough
struct.
B
In
that
line
of
thinking
there
was
one
thing
you
said
there
was
no
point
in
being
a
I.
I
continue
to
disagree
with
that
point,
but
everything
else
you
said
the
logic
close
okay.
E
E
B
E
B
Based
builders,
or
whatever,
that's
a
good
point
we
could
choose.
We
have
a
variety
of.
We
could
say
that
this
is
as
it
is,
and
then
for
the
other
ones.
We
could.
We
have
a
variety
of
levers
at
our
disposal.
We
could
no
pun
intended.
We
could
be
able
to
pass
this
by
ref
if
we
work
with
the
compiler
focus
on
that,
we
could
introduce
a
different
builder
for
that
purpose.
That
does
implement
eye
disposable.
We
could
yeah
whatever
we
can.
B
We
can
figure
it
out,
yeah,
okay,
so
for
right
now
we're
going
to
say
this.
One
is
not
this.
This
is
fine,
as
is
we.
J
B
It
does
span
two
string
with
the
appropriate
zero
comma
position,
storing
the
string.
It
then
does
a
local
array
equals
under
equals.
Underscore
pooled
array.
This
equals
default.
Clearing
itself
out.
If
pooled
array
is
not
null
return
to
pool
return
string
I'll
just
show
you.
A
Yeah,
my
I
will
say
my
initial
thought
with
that
is
well.
This
seems
bad
because
you
can't
say
that
someone's
not
going
to
call
tostring
more
than
once,
but
this
is
a
type
intended
just
for
the
compiler.
If
someone
grabs
this
manually
and
calls
two
string
and
that's
destructive,
I
I
think
I'm
okay
with
that.
C
E
H
If,
if
we
really
are
concerned,
for
whatever
reason,
we
could
always
have
an
analyzer
to
come
along
with
it,
that
basically
enforces
move
only
like
semantics,
but
that
might
be
more
work
than
we're
willing
to
do.
D
B
J
E
E
H
Display
attribute
on
this,
although
certainly
that
would
probably
be
a
good
idea.
E
A
I
mean
then
most
cases
f10
will
be
the
entirety
of
the
lifetime
and
you
don't
get
to
see
it,
but
if
or
there
may
be
cases
where
it
gets
weird
like
if
you
go
to
the
this
new
or
the
overload
that
steve
said
he
wanted
to
add.
If
you
step
into
that,
then
it
would
now
evaluate
the
the
argument
so
yeah.
A
No,
I
I
had
an
answer
for
this
a
couple
sessions
ago.
We
have,
alternatively
implemented
their
feature.
Yeah,
alternatively,
implemented
features.
B
C
B
E
The
the
only
thing
I
would
say
is
based
on
what
lever
just
suggested.
I
would
I
would
caution
us
with
thinking
we
can
solve
this
of
an
analyzer,
because
I
had
to
chat
with
jared
a
while
ago.
Basically,
what
you
would
have
to
track
is
every
time
the
compiler
makes
a
copy
of
a
struct
which
is
effectively
from
his
point
of
view
not
viable
as
an
analyzer,
because
the
the
apis
that
rosin
gives
you
are
not
rich
enough
to
do
that
reliably.
E
So
it
would
have
to
be
a
compiler
feature
that
would
have
to
like
think
about
more
apis
that
they
have
to
expose
so
that
you
can
actually
track
copies.
But
today
that
would
be
pretty
hard
to
write.
So
I
would
generally
say
we
should
be
happy
with
the
type.
If
we
think
that
needs
to
be
analyzed,
then
we
should
probably
do
something
differently,
but
I
mean
we.
B
A
C
A
B
The
concern
would
just
be
if
someone
somehow
was
stepping
through
I
mean
I'm
assuming
the
compiler
is
not
going
to
output.
You
know
pdb
markers
inside
of
the
generated
code,
so
it
would
only
be
for,
like
really
rare.
A
Right
it'd
be,
if
you
put
a
breakpoint
inside
on
line
133
here,
then
that
this
will
to
string,
and
that
may
not.
So,
if
you
put
it
in,
try
format
base
string,
then
the
this
will
call
tostring,
and
so,
but
really
the
question
is:
if
we
think
other
builders
are
going
to
want
to
do
the
I
expect
to
only
get
called
once
then
it's
do.
We
preemptively
say
that
you
know
we
want
to
call
it.
A
You
know
render,
or
something
and
just
in
terms
of
a
recommendation
right
well,
because
if
we
say
render
is
the
final
thing
and
that's
that
should
be
considered
as
destroying
the
state
of
the
object
then
or
that
like
renders
allowed
to
be
destructive,
then
that
avoids
the
oh.
Your
two
string
had
side
effects
and
while
debugging
it
caused
you
problems
and
yeah,
that's
kind
of
our
bad,
because
we
picked
two
string
as
that's
the
thing
to
you
like,
I
can
go
either
way.
I'm
just.
B
K
B
C
C
E
K
A
B
G
C
The
only
thing
that
can
ever
be
converted
to
a
string
is
this
pattern.
A
Okay,
so
in
in
the
in
the
other
builders,
you
know
the
builder,
because
it's
the
it's
the
target
type
of
the
value,
correct,
correct,
there's
not
like
a
attribute
you
put
on
the
method
which
is
use
this
alternative
builder
implementation
and
correct
it's
okay.
So
if
it
only
matters
for
this
type,
then
I
think
two
string
is
fine
and
it's
not
precedent
establishing,
because
it's
just
limited
to
this
type.
It's
not
how
other
builders
will
work
in
the
future
they
can,
if
they
want
to
have
a
similar.
B
Okay,
that
completes,
I
believe,
yeah
that
completes
proposal
one.
We
have
half
an
hour
to
see
how
far
we
can
get
through
this
okay.
So
one
note
word
of
warning.
Everything
we've
talked
about
thus
far
has
been
kind
of
agreed
upon
for
c-sharp
language
functionality.
B
Some
of
the
things
we're
going
to
look
at
here
are
being
proposed,
but
haven't
yet
been
sort
of
in
blood
signed
for
c-sharp,
so
there
might
be
some
kind
of
minor
tweaks
or
changes
that
happen
here
or
something
happens
and
all
just
blows
up
entirely,
but
I
wanted
to
bring
it
through
now
to
be
able
to.
You
know,
root
out
any
problems
and
get
things
moving.
B
B
You
want
to
be
able
to
use
this.
This
as
part
of
the
format.
Just
passing
is
a
format
method
after
the
formatting
has
already
happened,
it's
too
late,
so
we
need
some
way
to
tell
the
compiler
when
you
generate
the
code
for
this,
and
you
call
the
create
method,
look
for
a
create
method
that
not
only
takes
the
base
length
base
length
and
the
whole
count.
B
Also
look
for
one
that
takes
a
an
I
format
provider
and
pass
this
guy
in
to
the
create
method,
and
this
allows
us
to
pass
get
additional
state
from
the
call
site
into
the
builder.
So
in
this
example,
this
you
know
kind
of
gets
generated,
we're
calling
interpolated
stringbuilder.create
passing
in
cultureinfo.invariant.
B
We
also
end
up
passing
it
into
format,
just
because
that's
what
the
method
takes,
but
format's
not
going
to
use
it.
So
we
need
an
attribute
to
do
that
and
I
propose
just
interpolated
builder
argument
attribute
again.
This
is
only
relevant
for
someone
doing
exposing
methods
that
take
builders
that
you
know
pass
an
additional
state.
The
vast
vast
vast
majority
of
customers
aren't
going
to
see
this.
B
Our
vast
majority
of
developers
aren't
going
to
see
this
yeah.
But
again,
this
is
some
this
this,
how
the
exact
mechanism
by
which
that
is
passed
and
hasn't
been
agreed
on
yet
so,
assuming
it's
of
an
attribute
that
goes
on
the
builder
in
the
method,
signature,
I've
suggested
this.
C
My
only
quibble
there
is
allow
multiple.
It
should
probably
be
false.
B
Yeah,
I
did
that
because
I
wasn't
sure
if
we
would
want
to
allow
someone
saying
interplay
builder
argument
argument.
One
interpolated
builder
argument,
argument,
two
etc.
B
Fine,
a
lot
of
multiple
false
find
them
by
me.
Any
other
thoughts
on
the
attribute.
B
C
Okay
and
and
the
order
in
the
interpolated
in
in
that
argument,
array
right
is
the
order
that
you
specified.
So
it's
not.
You
know
if
you
happen
to
take
three
ins
or
if
you
happen
to
take
four.
Instead,
you
swapped
and
you
accidentally
swapped
the
names
of
some
things
you
didn't
like.
You
didn't
mean
to
have
the
order
that
you
gave
them
in
you
know
you
will
you'll
mess
up.
A
But
yeah
we
will
at
some
point
because
I
think
we
skipped
over
looking
at
the
create
method
and
naming
of
the
parameters
on
the
builder.
But
we'll
want
to
pop
back
and
do
that.
H
A
H
Are
are
the
parameters
still
evaluated
left
to
right,
regardless
of
what
order
they're
specified
in
that
attribute.
C
The
parameters
are
evaluated
left
to
right,
as
the
user
wrote
them.
So
if,
if
you
had
two
parameters
and
one
of
them
and
like
they
were
opposite
order
in
the
create
call,
as
they
were
written
in
source,
they
will
be
evaluated
in
source
order
and
then
reordered
for
the
create
call.
H
C
C
The
only
question
the
only
question
that
we
still
have
here
that
really
needs
to
be
cleared
up
is
what
happens
if,
like
you
have
one
of
the
parameters
is
after
the
interpolated
string,
because
we
can't
evaluate
the
contents.
They
interpolate
a
string
before
the
parameter
needed
to
create
the
contents
of
the
interpolated
string.
C
So
there's
there's
some
odd
questions
there
that
we
will
need
to
resolve,
but
yeah.
B
We
don't
in
the
things
that
I
propose.
I
don't
believe
I
have
anything
that
hits
that
case,
but
so
I
think
we
would
be
fine
just
say
we
just
don't
allow
that
so.
C
A
A
B
B
K
Based
on
the
potentially
renaming
it
to
append
in
format
would
format
count
be
a
better
name.
A
Yeah
yeah
formatted
count
interpolation
count,
you
know,
but
we
got
rid
of
the
word.
Whole.
So
whole
seems
weird.
H
C
C
B
All
right
so
now
we
get
into
cool
new
scenarios
that
we
enable
with
interpolated
with
interpolated
strings
syntax.
So
imagine
that
you
had
a
struct
point
and
you
wanted
to
implement
I
spam
to
span
formattable
on
that.
So
you
need
to
implement
this
api
today.
You
would
do
something
like
this
you'd
say
all
right.
I
want
to
format
x
to
the
destination.
B
If
I
couldn't
do
it,
I'm
going
to
return
false
and
then
I'm
going
to
slice
and
then,
if
there's
length,
if
there's
space
left
for
a
comma
space,
because
I
want
x,
comma
space
y,
then
you
know
do
the
copy
and
you
know,
keep
track
of
how
many
I've
written
and
then
slice
again
and
then
format
y
and
if
we
couldn't
fit
it
return
false
and
then
figure
out
the
total
number
of
written
and
return.
B
True,
and
that's
just
for
two
pieces
of
data,
it
gets
way
more
complicated
when
it
starts
being
more
than
that.
Imagine
you
could
instead
write
this
where
you
say
I
want
to
write
this
interpolated,
this
interpolation
using
this
provider
and
it
still
returns
a
bool
still
tells
me
how
many
characters
are
written
and
under
the
covers.
The
compiler
essentially
generates
the
equivalent
of
that
for
you
via
the
builder
pattern.
B
How
do
we
do
that?
Well
and
again,
lots
of
names
here
to
consider
and
if
we
don't
care
about
the
scenario,
but
an
extension
method.
Just
you
know,
memory
extensions
has
a
whole
bunch
of
extensions
on
spam,
so
we
add
a
I've
called
it
try
right
for
now.
That's
debatable.
One
overload
that
just
takes
the
span
and
an
interpolated
span.
Builder
and
char
is
written
and
another
that
takes
the
span
and
a
provider
and
the
builder
and
outputs
charge
written
and
then
the
interpolated
span
builder,
which
looks
exactly
you
know.
B
B
What
differs
is
the
name
and
different,
create
methods
in
addition
to
taking
those
two
things:
it
takes
a
destination
and
provider
in
this
case
and
then
we'll
notice.
Two
differences
across
the
whole
thing.
One
is
this
outbull
success
and
one
is
that
these
are
all
now
bull
returning
all
of
these
bools.
B
To
get
back
to
the
question
that
eric,
if
he's
still
on
the
call,
I
don't
think
he
is
asked
at
the
beginning,
which
is
what
does
the
compiler
do
when
you
have
bools
in
this
situation
and
the
answer
is
it
allows
for
short
circuiting?
So
basically,
if
the
moment,
one
of
these
calls
starts
returning
false,
the
compiler
doesn't
evaluate
anything
further
and
what
this
lets
you
do
is
in
interpolation
span
builder,
for
example.
B
B
If
it's
false,
we
can
stop
doing
work
immediately,
because
we
know
this
whole
thing
just
isn't
going
to
work,
so
success
ends
up
being
false
and
then
we
don't
make
any
of
these
tri
format
calls.
Similarly
as
we're
going
through.
If
any
one
of
these
says,
I
don't
have
room
to
fit
the
data,
it
returns
false
and
the
rest
of
them
are
short-circuited
out
and
we
don't
do
any
more
formatting.
That
span
builder
ends
up
storing
that
success
value
as
well.
B
So
when
this
builder
ends
up
getting
passed
to
try
right,
try
right
just
looks
at
the
builder
and
says
if
builder.success
then
charge
written
equals.
However,
many
char
characters
were
stored,
returned
true
else
charge
charles
written
equals.
Zero
return
false,
and
this
is
how,
by
exposing
this,
we
enable
the
developer
to
write
this.
B
So
let
me
come
back
to
this
in
a
moment.
Let
me
show
some
of
the
other
examples
as
well.
There's
we
want
to
support
string
formatting
with
a
provider,
so
today
there's
the
string
format
method.
You
can
pass
in
your
format,
plus
all
of
your
arguments.
You
can
also
pass
in
a
provider
your
format
and
all
your
arguments.
We
can
instead
expose
this
format
method
which
takes
that
same
interpolated
string
builder
or
a
different
one.
If
we
wanted
and
the
provider
the
provider
ends
up
getting
passed
to
the
create
method.
B
B
We
can
also
support
using
like
by
default
today,
if
you
just
did
this
or
if
you
did
what
we
saw
with
the
previous
proposal
right
now,
it
immediately
is
renting
an
array
from
the
array
pool
to
support.
However
much
state
you
might
pass
in,
but
we
can
support
if
we
allow
you
to
pass
in
a
oh.
I
lied
in
this
proposal.
I
do
have
this
coming
after.
We
could
move
that
if
we
wanted
to,
we
could
move
that
to
the
before.
B
You
could
write
this
and
now
we
would
start
off
using
this
stack
space
as
part
of
the
formatting
rather
than
going
to
the
to
the
array,
or
you
might
have
some
pre-allocated
giant
buffer
that
you
wanted
to
use,
and
you
could
use
that
for
everything.
You
pass
that
in
here
and
again.
B
The
compiler
is
just
passing
that
in
here,
so
it
starts
to
enable
these
additional
possibilities,
or
this
is
one
of
my
favorites,
the
the
number
of
cases,
if
you
search
like
the
net
runtime
repo,
in
particular
in
the
sdk
or
you
search
in
asp.net,
the
number
of
places
you'll
see
stringbuilder.append
with
a
string
interpolated
argument,
so
it's
basically
creating
a
string
and
then
passing
that
string
into
append.
B
It
is
much
larger
than
you
would
like
to
believe,
but
we
can
enable
you
to
just
write
sp
append
format
with
this
string,
interpolation,
syntax
and
actually
have
it
generate.
Like
the
you
know,
the
string
builder
is
passed
into
this
format
builder,
and
then
each
of
these
is
actually
appending
directly
to
the
string
builder.
So
you
get
to
write
this
nice
thing.
B
So
we
can
start
enabling
these
kinds
of
cool
things,
nice,
syntax
and
efficiency
rolled
together
in
one
nice,
pretty.net,
six
c,
sharp
ten
bundle.
That's
the
summary
of
part
two.
There
are
other
things
that
I
haven't
proposed
that
we
could
do
elsewhere.
For
example,
we've
got
utf-8
formatter.
B
We
could
add
a
similar
try
right
to
utf-8
formatter
with
a
builder
that
accepted
a
read-only
span
of
byte,
and
now
you
can
all
the
complicated
code
we
have
where
we're
formatting
utf-8
can
also
end
up
using
interpolated
strings
and
everything
gets
ends
up
being
output
as
part
of
utf-8.
I
haven't
proposed
that
because
I'm
not
sure
how
you,
how
commonly
we
it
would
be
actually
used,
but
it's
the
kind
of
thing
we
could
look
at
in
the
future.
A
So,
okay,
so
when
so
fred
had
said
something
about
like
can't
make
it
ref
when
I
said
it
should
be
ref
for
the
string
format,
I
format
provider
and
interpreted
interpolated
string
builder.
This
is
because
we
would
need
to
enhance
the
language
to
say
that
you
can
do
ref
dollar
sign,
quote
right
or
or
that
the
compiler
simply
understands
that
dollar
sign
quote,
can
go
to
a
ref.
H
A
C
I
don't
know
what
that
means,
and
then
in
the
in
the
other
case,
we
already
have
enough
people
complaining
about
how
we
allow
people
to
do
in
silently
now.
Imagine
that
we
allowed
them
to
do
ref
too
yeah,
but.
B
That
said,
you
know
that
the
the
only
case
that
that
actually
matters
like
out
of
all
the
builders
we've
talked
about
the
only
one.
That's
wrapping
a
returnable
resource
is
the
interpolated
string
builder
the
span
one.
It's
just
right:
wrapping
the
span
that
was
passed
in
there's
no
resource
to
be
cleaned
up.
In
the
string
builder
case.
It's
just
wrapping
the
string.
Oh,
where
is
that
the.
A
B
No,
this
this
one's
a
rough
structure.
It
has
to
be
because
it
wraps
the
span.
Sorry
this
one,
because
it
wraps
this
guy.
A
Okay,
fair
enough,
but
yes,
it's
really
it's
because
interpolated
string
builder
is
a
mutable
struct
that
is
doing
resource
management,
which
is
the
the
scary
piece
but
yeah
I
mean
I.
I
know
that
I'm
not
you
know
ldm
and
I'm
not
even
on
the
rosslyn
team.
So
I
don't
get
all
the
complaints
of
things
like,
but
in
and
as
a
as
a
reference
type
are
different.
Why
did
you
let
in
be
implicit?
B
Think
that
it's
not
too
much
magic.
I
also
originally
proposed
passing
these
by
ref,
so
I
actually
agree
with
you,
okay,
but
we
need
to
work
it
out
with
the
compiler
hooks
right.
A
A
Well,
yeah,
because
because
we'd
be
adding
it
on
on
as
string.format
and
it's
now
sort
of
leaking
out
and
people
may
look
at
like,
I
want
to
go
build
these
things
it's
like
well,
you
can.
A
Yeah,
then
the
whole
thing
goes
away
and
var
says:
dollar
sign
quote
is
string
right,
yes,
yeah.
C
Yeah,
so
there
are
a
couple
of
interesting
overload
resolution
rules
that
are
important
to
know
about
when
we're
talking
about
these
things.
If
you
have
an
overload
that
takes
a
type
that
can
be
a
builder
I.e
has
has
the
append
and
a
append
formatted
methods
for
every
one
of
these
things,
and
there
is
a
create
method
either
that
just
takes.
C
C
It
will
or
or
do
do
a
different
thing
when
you,
when
you
upgrade
when
you
update
your
library
to
a
new
version
or
your
users
update
the
version
of
the
library,
and
so
if
you
extract
to
a
local
variable
and
then
you're
using
that
when
you
have
a
string
overload.
Instead,
well,
that
could
potentially
call
something,
let's
call
something
different
and
do
a
different.
C
C
C
We
will
likely
want
to
update
refactorings
or
what
have
you
to
either
not
show
that
or
to
make
sure
that
it
creates
it
with
like
the
specific
type
involved,
or
has
some
warning
that
says
this
changes
semantics
or
you
know
something
like
that.
B
Okay,
so
I
think
the
first
question
for
this
one
is:
do
people
agree
that
this
is
a
helpful
thing
to
expose?
You
know
being
able
to
write
this
instead
of
that.
A
A
I
A
So
from
the
language
perspective,
where
you
showed
the
generated
change
with
your
your
success,
waterfall
yeah,
so
the
the
rule
here
is
create,
takes
two
ants.
A
If
it
takes
other
things,
then
they
get
bound
by
that
attribute
and
it's
allowed
one
out
bull
as
an
optional
thing,
yeah
and
okay,
and
so
the
out
bool
success
is.
Is
that
required
for
the
appends
to
be
bull
returning
or
does
it
figure
out
like?
Is
that
one
allowed
to
be
sort
of
voidish?
And
then
all
the
opinions
can
be
this?
This.
B
C
Yeah
and
the
reason
for
example,
say
you
have
a
logging
framework.
The
logging
framework
is
gonna
check
to
see
whether
or
not
the
log
level
is
enabled
during
create,
but
then
the
actual
formatting
of
each
hole
is
that's
going
to
succeed
right.
It's
always
going
to
succeed.
C
I
don't,
I
don't
think
it
ver.
I
don't
think
that
scenario
is
very
likely.
I
think
it's
almost
certain
that,
if
you're
going
to
if
it
if
the
hole
itself
is
going
to
successfully,
do
it
then
create
is
also
going
to
be
able
to
tell
it,
but
we're
not
tying.
A
Okay,
and
and
because
there's
never
an
implicit
string
off
of
these,
that's
why
the
pattern
here
is
this:
just
changes
the
cascade
call
into
the
builder,
and
then
it
passes
the
builder
in
whatever
state
it
got
into
from
the
short
circuit
and
it's
up
to
the
destination
to
understand.
The
builder
did
something-
and
you
may
not
be
happy
with
that.
That's
correct.
B
E
B
Let's
say
this
method
ends
up
taking
up
too
much
space,
and
so
it
returns
false
in
addition
to
returning
false,
it's
also
going
to
store
a
false
value
into
the
builder.
The
builder
has
a
field
on
it,
a
private
field
success
or
an
internal
field
success.
B
A
C
Well,
that's
something
we're
still
debating
because
there's
there's
a
couple
of
complicated
scenarios
there
like,
for
example,
if
you
are
you
have
a
class
builder
type
and
you're
say
on
like
an
abstract
super
class,
then
it
could
return
you
and
implement
an
object
that
you
don't
know
at
compile
time
implements
like
disposable
but
could
implement
it
at
runtime,
and
so
there's
like
for
each,
for
example,
we'll
do
an
if
thing
is
dispose
disposable
dispose
and
so
the
you
know
we
can.
C
We
can
figure
it
out
statically
for
structs
or
for
sealed
types,
but
we
can't
necessarily
figure
it
out
for
either
class
types,
unsealed
class
types
or
interfaces
you
can.
You
can
use
an
interface
with
this
thing
once
we
get
abstract,
statics,
so
fair
enough.
A
And
so
the
okay,
but
really
because
the
only
time
that
you
then
are
creating
these
is
when
someone
is
doing
the
the
either
target
typing
from
the
method
or
or
they
declared
it
to
a
local
yeah
target
typing
in
some
fashion.
Oh
because
it's
a
thing
that
we'll
have
to
care
about
an
api
review
in
the
future.
C
That's
failure
to
compile
multiple
builder
types
are
not
no
builder
type
is
considered
more
applicable,
even
if
one
of
them,
for
example,
has
the
interpolated
string
builder
argument
attribute
on
one
of
the
methods
and
the
other
one.
Just
is
a
builder
type
that
takes
arbitrary
things.
We're
not.
We
could
do
that
right,
like
we
could
make
a
distinction
between
methods
that
have
a
builder
type,
just
via
the
argument,
type
being
a
builder
type
and
the
methods
that
have
the
argument
that
take
in
context
from
the
method.
C
But
currently
the
thought
is:
that's
that's
unnecessary.
Okay,.
A
C
As
long
as
the
right
ambiguity,
as
long
as
the
rest
of
the
signature
matches
up
as
well.
A
But
this
is
the
like.
You
know
this
is
the
null
literal
problem,
but
worse
because
with
no
literal,
we're
like
well
most
things
if
you're
overloading
it
null
probably
was
already
throwing,
and
so
it's
fine
it
wouldn't
have
worked.
If
you
wrote
the
word
null,
but
now
it's,
if
you
have
a
dollar
sign
quote,
then
overloading
can
now
cause
the
compile
to
fail
in
ways
that
the
user
can't
see
or
really
react
to.
So
it's
just.
C
I
don't
know
if
that's
an
interesting
question
the
way
the
spec
is
written
today,
I
don't
think
you
could
just
cast,
but
that
is
a
question
that
I
think
we
we
could
resolve
like
we
could.
We
could
allow
that
right.
A
A
B
A
Yeah,
that's
that's
fine,
I'm
I'm
just
thinking
through
the
consequences
of
design
on
future
api
and
overloading
things,
which
is
a
little
different
than
talking
about
the
api
that
you
have
proposed
here.
I'm
aware,
but
it
was
the
like.
Oh
wait,
there's
now
a
new
kind
of
breaking
or
there's
a
new
non-obvious
breaking
change
to
our
overload
resolution
breaks.
E
I
mean
I'm
honestly
more
concerned
about
the
the
constraint
that
you
kind
of
have
to
put
the
literal
into
the
argument
position,
because
people
frequently
put
stuff
in
locals
right
and
that
that
all
of
that
stuff
makes
it
a
lot
more
complicated.
To
do
that,
I
mean,
if
you
do,
that,
though,
like
it
won't.
J
A
A
Smart
enough,
it
would
need
to
save
it
would
need
to
say
whatever
is
off
screen
right,
temp
equal
new,
that
of
the
span,
I
guess-
or
of
the
counts
in
this,
but
like.
I
A
E
A
B
A
B
Accept
a
certain
position,
yeah!
No!
I
agree.
I
wasn't.
I
wasn't
losing
back
anybody
trying
to
clarify
that.
Usually,
when
someone
does
a
refactoring,
it
ends
up
doing
something
wrong.
We
care
more
about
when
it
when
it
compiles
and
then
runs
and
just
happens,
to
have
suddenly
different
behavior
at
runtime
and
I'm
suggesting
that
in
the
99.9
case
it's
not.
It's
gonna
like
put
an
error
in
their
face
and
say
like
right:
yeah
don't
do
that.
C
E
C
I
would
assert
that
for
many
of
these,
there
are
going
to
be
either
string
based,
overloads
or
like,
because
many
the
way
these
rules
were
designed
was
such
that
people
could
add
these
to
existing
apis
that
already
take
a
string
and
and
make
them
better
yeah.
So
I
I
would
say
that
there
is
the
potential
for,
for
that.
B
J
A
A
E
A
B
A
Yes,
there
we
do
have
string
that
format.
That
takes.
Oh
sorry,
we
need
one
that
takes
an
I
format
provider
in
the
first
argument,
because,
with
an
I
format
provider
in
the
first
argument,
instead
of
a
string
there's
now
nothing
that
is
params
object
in
the
second
parameter,
because
it
still
needs
the
string.
B
C
C
E
Well,
I
mean
that's
one
option
to
fix
it.
I
mean,
like,
I
think,
the
the
example
that
we
just
talked
about
right.
It
would
still
do
the
right
thing
like
you
would
end
up
with
the
correctly
formatted
string.
It
would
just
be
not
as
performant
right.
So
that's
an
example
when
analyzer
and
component
code
fix
it
could
actually
help.
You
say
well,
move
this
thing
from
a
local
direct
into
the
argument
chain
to
make
it
more
effective,
more
efficient
right,
so
that
that
would
be
the
way
you
would
promote
it.
I
think.
B
A
That's
true
yeah
and
I
don't
I
think,
that
string
dot
format
if
it
found
a
string
that
looked
like
open,
curly,
zero
and
then
you
it
closed
curly.
And
then
you
didn't
have
any
objects
in
the
array
I
will
throw,
I
think,
it'll
throw
so
you
could
factor
it
out
to
a
local
and
now
it
throws
instead
of
prints
again
very,
very
edge
case.
A
But
why
would
it
if
you
ended
up
printing,
something
that
was
like
the
result
is
open,
curly
answer
or
like
literal
open
curly
is
what's
going
to
get,
him
is
in
the
output
string
and
then
you're
like
the
result
is
zero
and
curly
braces
instead
of
square
braces
or
parens
or
quotes
or
whatever
other
thing
you
wanted
and
then
now
it's
like
wait.
That's
a
format.
String
that
used
a
positional
parameter
that
you
didn't
give
me
throw
oh.
E
B
A
B
C
Yeah,
I
do
think
that
we
might,
we
might
end
up
requiring
that
arguments
be
in
front
of
the
of
the
element.
B
That's
fine,
I
was
just
saying
like
we
can
only
provide
this
overload
and
move
this
here,
in
which
case
there's
no
way
that
could
be
confused
with
any
existing
overload
on
string
format
of
string
format.
A
Right
but
then
you
can't,
if
you
make
the
oh,
you
only
have
the
the
overload
that
takes
it
in
the
syntax.
Not
you
get
rid
of
the
simple
create
off
of
interpolated
string
builder.
I
was
like
you're
going
to
kill
the
whole
feature
just
to
fix
this.
No.
B
I'm
just
saying
this
guy,
you
just
you
know
we
move
sorry,
we
move
this
guy
earlier,
which
we
need
to
do
anyway,
and
then
we
only
expose
this
one.
We
don't
expose
that
one
and
then
there's
there's
nothing
on
four
string
format.
Today.
That
has
a
second
argument.
That
is
a
spam
right.
A
Yeah,
because,
what's
weird,
is
I
totally
buy
the
compiler's
argument
for
why
the
parameters
have
to
come
first,
because
order
of
operations
is
insane,
but
the
like.
Certainly
looking
at
this
line
of
code
I'm
like,
but
the
culture
info
should
be
the
second
parameter,
because
that's
the
less
important
one.
A
B
What
I
was
initially
doing,
which
I
decided
was
a
bad
idea
after
well.
I
waxed
and
waned
on
it,
but
I
initially
had
this
on
the
interpolated
string
builder,
but
I
didn't
realize
no,
I
really
don't
want
to
push
people
to
use
this
type
that
we
just
put
in
compiler
services,
so
I
moved
it.
D
B
A
I
don't
know,
I
know
why
we
would
do
it.
This
is,
do
we
have
a
precedence
for
the
name.
B
We
don't
so
I
I
think
I
went
through
four
iterations
and
I
was
like
I'll
wait
for
jeremy
and
emo
to
tell
me
what
it
should
be.
A
I
mean
because
because
if
that's
the
only
span,
it's
willing
to
use
right
if
it's
use
this
space
or
fail
well,
no,
in
this
case
it's
start
with
the
space
and
then
grow
into
the
array
pool.
If.
B
You
need
to
okay
in
in
this
case
it's
this
is
the
difference.
Yeah.
A
Yeah,
like
I
agree
that
the
total
the
concept
of
scratch
buffer-
I
don't
know
that
that's
a
name
that
we
really
want
to
use
like
temp
span
also
feels
weird.
A
Yes,
well
in
this
will
do
something
sad
from
the
compiler,
because
it
can't
match
your
your
name
of.
Can
you
use
name
of
there
yet.
C
E
C
We
have
we
have
a
open
issue
that
I
think
we're
trying
to
get
in
for
10..
So.
E
Pretty
pleased,
I
think,
the
I
think
scratch
that
sounds
similar.
Don't
they
have
another
api,
maybe
that
you
can
pass
in
the
buffer.
H
E
I
probably
added
one
for
one
of
our
json
wants
it.
I
forgot,
I
thought
I
thought
we
had
one
that
did
that
at
least.
E
A
And
I'm
gonna
make
levi
if
he's
still
yeah
he's
still
here
want
to
punch
me,
hi
utf-8
string,
question
mark.
A
Well
so
this
is
if,
if
we
think
utf-8
string
is
going
to
happen
in
six,
which
maybe
we
don't,
but
if
we
think
it's
going
to
happen,
we're
adding
more
things
that
are
like
the
the
local
length
and
stuff
those
are
again
tied
to
ucs2
or
sorry,
utf-16,
there's
a
difference,
and
so
it's
that's
really.
The
only
question,
and
once
we
start
talking
about
like
literal
length
and
stuff
is,
do
we
need
to
care
about
utf-8ness
here
or
is
it
still?
A
You
know
what,
where
a
utf-16
based
language
and
runtime
deal
with
it,
I'm
fine.
H
With
that,
I
just
asked
I
always
just
interpreted
length
as
like
the
number
of
elements
in
the
backing
buffer.
Those
elements
might
be
utf-16,
car,
chars,
utf-8,
bytes
whatever,
but
it's
a
number
of
elements
in
the
buffer.
H
Yeah
that
would
that
would
be
improper,
like
that.
That's
one
of
the
problems
that
I'm
actually
running
against
right
now
with
some
of
the
stream
stuff
that
I'm
doing,
because
it's
at
that
point
it
really
just
becomes
a
best
guess
more
than
anything
else
like
you
can,
you
can
say
here's
what
the
worst
case
scenario
can
be,
but
until
I
actually
analyze
all
the
data,
I
can't
give
you
a
proper
number.
A
B
I'm
not
clear
what
the
question
is.
I
mean
I'm
assuming
if
we
ever,
if
we
ship
a
utf-8
string,
we'll
add
a
utf-8
string,
dot
format
which
has
its
own
builder,
that's
based
on
bytes,
instead
of
chars,
fair.
A
H
C
B
H
B
All
right:
well,
we
are
15
minutes
over.
I
feel
like
we're
pretty
much
settled
on
part
one,
and
we
need
more
time
to
talk
about
part
two.
E
E
We
should
probably
for
thursday
reserve
one
more
hour
on
this
and
then
try
to
get
it
done
and
then
check
out
the
backlog.
B
A
Okay,
so
I
I
took
notes,
I'm
gonna
read
what
I
have
for
part
one,
because
steve
has
the
the
screen
right
now
part
one:
why
do
we
need
the
interpolation
hole
version
for
string?
The
answer
is
to
specialize
out
of
t
or
object
and
to
avoid
universal
formatting
problems,
which
is
why
we
needed
the
pen
literal
interpolated
string
builder.
It
is
important
that
it's
a
refstruct
and
we
will
make
it
work
in
async,
we'll
have
an
answer.
We
don't
need
to
do
anything
special,
for
I
form.
A
B
B
A
Sold
should
we
support,
void,
star
or
t
star
we're
happy
with
no
do
we
need
it
to
be
eye
disposable,
we're
happy
with
no-
and
I
can
remove
this
note
about
the
language
needing
to
support
it
in
general
case,
because
there's
no
general
case,
we
decided
to
string
shouldn't
be
destructive,
so
we
add
a
string
in
clear
we,
which
is
what
we
want
the
compiler
to
call
for
us
and.
H
A
A
Thank
you
and
the
final
note
interpolated
stringbuilder.create.
We
want
to
rename
the
parameters
to
be
a
literal
length
and
formatted
count
to
match
the
method
names,
and
you
also
had
to
know
that
you
really
want.
We
really
want.
B
A
This
is
for
part
two
nevermind
yeah,
so
for
part
two
I
have
the
we
should
take
the
builder
as
ref
and
allow
multiple
should
be
false
on
the
attribute.
Those
are
the
only
notes
that
I
took
because
that's,
I
think,
the
only
definitive
things
we
said.
G
A
Cool
so
so
I
think
we're
done
with
part
one
and
it's
approved
with
feedback
and
at
some
point
someone
should
update
the
api
proposal
to
match
it.
I'll
do
that.
Thank
you,
steve.
A
A
All
right
so
with
that
thanks
everybody
and
at
least
on
the
u.s
pacific
coast,
it
is
now
lunchtime
so
see
you
all
next
time.
Thank
you.
Awesome.