рдмрд╣реБрдд рдкрд╣рд▓реЗ рдирд╣реАрдВ, рдореИрдВрдиреЗ рд╕реНрд╡рдЪрд╛рд▓рд┐рдд рд░реВрдк рд╕реЗ рдХреИрд╢рд┐рдВрдЧ рдХреЗ рд▓рд┐рдП рдПрдХ рдЫреЛрдЯрд╛ рд╡рд░реНрдЧ рд▓рд┐рдЦрд╛ рдерд╛ рдФрд░ рдордирдорд╛рдирд╛ рдореВрд▓реНрдпреЛрдВ рдХреЛ рдЕрдкрдбреЗрдЯ рдХрд┐рдпрд╛ рдерд╛ред рдЗрд╕рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдирд╛ рдмрд╣реБрдд рдЖрд╕рд╛рди рдерд╛ - рдпрд╣ рдХреЗрд╡рд▓ рдЕрддрд┐рднрд╛рд░рд┐рдд рдЕрджреНрдпрддрди рдкрджреНрдзрддрд┐ рдХреЗ рд╕рд╛рде рдПрдХ рдЕрдирд╛рдо рд╡рд░реНрдЧ рдмрдирд╛рдиреЗ рдХреЗ рд▓рд┐рдП рдЖрд╡рд╢реНрдпрдХ рдерд╛, рдФрд░ рдлрд┐рд░, рдЬрдм рдЖрд╡рд╢реНрдпрдХ рд╣реЛ, рдореВрд▓реНрдп рдЕрдкреНрд░рдЪрд▓рд┐рдд рдХреЛ рдЪрд┐рд╣реНрдирд┐рдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдлрд╝рдВрдХреНрд╢рди рдХреЛ рдХреЙрд▓ рдХрд░реЗрдВ рдФрд░ рд╕реНрд╡рдпрдВ рдореВрд▓реНрдп рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП:
public static void main(String[] args)
{
LazyValue<Integer> ultimateQuestionOfLife = new LazyValue<Integer>()
{
@Override
protected Integer update()
{
return findNewUltimateAnswer();
}
};
//
ultimateQuestionOfLife.invalidate();
// update()
System. out .println( "Answer is: " + ultimateQuestionOfLife.get());
// update() ,
System. out .println( "Answer is: " + ultimateQuestionOfLife.get());
//
ultimateQuestionOfLife.invalidate();
// update()
System. out .println( "Answer is: " + ultimateQuestionOfLife.get());
}
рдПрдХ рдЫреЛрдЯреЗ рдИрдЯреНрдпреВрдб рдХрд╛рд░реНрдпрдХреНрд░рдо рдореЗрдВ рдкрд░реАрдХреНрд╖рдг рд╕рдлрд▓ рд░рд╣реЗ, рдЬрдмрдХрд┐ рдЗрд╕ рд╡рд░реНрдЧ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдиреЗ рд╡рд╛рд▓реЗ рдПрдХ рдмрдбрд╝реЗ рдХрд╛рдо рдХреЗ рдкреНрд░реЛрдЬреЗрдХреНрдЯ рдореЗрдВ рдПрдХ рд╕реНрдЯреИрдХ рдУрд╡рд░рдлреНрд▓реЛ рддреНрд░реБрдЯрд┐ рджрд┐рдЦрд╛рдИ рджреЗрдиреЗ рд▓рдЧреА - рдорд╛рдиреЛрдВ рдиреЗ рдПрдХ рджреВрд╕рд░реЗ рдХреЛ рд╕реВрдЪрдирд╛ рдХреЗ рдХрд┐рд╕реА рдЕрдиреНрдп рд╕реНрд░реЛрдд рдХреЗ рдмрд┐рдирд╛ рдЕрдкрдбреЗрдЯ рдХрд┐рдпрд╛ред рдпрджрд┐ рд╣рд░ рдмрд╛рд░ рдкреБрдирд░реНрдЧрдгрдирд╛ рд╣реБрдИ рдФрд░ рдЕрдВрддрд┐рдо рдХреНрд╖рдг рдореЗрдВ рдирд╣реАрдВ, рддреЛ рдпрд╣ рддреНрд░реБрдЯрд┐ рдирд╣реАрдВ рд╣реЛрдЧреАред
private static LazyValue<Integer> lv1 = new LazyValue<Integer>()
{
@Override
protected Integer update()
{
return lv2.get(); //
}
};
private static LazyValue<Integer> lv2 = new LazyValue<Integer>()
{
@Override
protected Integer update()
{
return lv1.get() + 1;
}
};
public static void main(String[] args)
{
// StackOverflowException
System. out .println(lv2.get());
}
рдмрд╣реБрдд рдЬрд▓реНрджреА, рдореИрдВ рдпрд╣рд╛рдБ рдФрд░ рд╡рд╣рд╛рдБ рдкреБрдирд░рд╛рд╡реГрддреНрддрд┐ рдХреЛ рд░реЛрдХрдиреЗ рдХреЗ рд▓рд┐рдП рдХреЛрдб рдореЗрдВ рдмреИрд╕рд╛рдЦреА рд╕рдореНрдорд┐рд▓рд┐рдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдердХ рдЧрдпрд╛, рдФрд░ рдореИрдВрдиреЗ рдХреИрд╢рд┐рдВрдЧ рдХреНрд▓рд╛рд╕ рдореЗрдВ рдПрдХ рдкреБрдирд░рд╛рд╡реГрддреНрддрд┐ рдбрд┐рдЯреЗрдХреНрдЯрд░ рдХреЛ рдПрдореНрдмреЗрдб рдХрд░рдиреЗ рдХрд╛ рдлреИрд╕рд▓рд╛ рдХрд┐рдпрд╛, рдЬреЛ рдХрд╛рдо рдХрд░реЗрдЧрд╛, рд░рд┐рдХрд░реНрд╕ рдХреЗ "рдЗрдВрд╕реНрдЯрд┐рдЧреЗрдЯрд░" рдХреЛ рд╕реНрдЯреИрдХ рдХреЛ рдЦреЛрд▓рдирд╛ рдФрд░ рдХреБрдЫ рдбрд┐рдлрд╝реЙрд▓реНрдЯ рдореВрд▓реНрдп рдХрд╛ рдЙрддреНрдкрд╛рджрди рдХрд░рдирд╛, рдЬрд┐рд╕рд╕реЗ рд░реЛрдХрдирд╛ред StackOverflowExceptionред рдпрд╣рд╛рдБ рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди рд╣реИ:
private static LazyValue<Integer> lv1 = new RSLazyValue<Integer>()
{
@Override
protected Integer update()
{
return lv2.get();
}
@Override
protected Integer getDefault()
{
return 0;
}
};
private static LazyValue<Integer> lv2 = new RSLazyValue<Integer>()
{
@Override
protected Integer update()
{
return lv1.get() + 1;
}
@Override
protected Integer getDefault()
{
return 10;
}
};
public static void main(String[] args)
{
// 10
System. out .println(lv2.get());
}
рд╕рднреА рдЬрд╛рджреВ RSLazyValue рд╡рд░реНрдЧ (RS Recursion-Safe) рдореЗрдВ рд╣реИред рдЬрд┐рд╕ рд╕рдордп рдЕрдкрдбреЗрдЯ рд╢реБрд░реВ рд╣реБрдЖ рд╣реИ, рдЙрд╕ рд╕рдордп рдПрдХ рд╡рд┐рд╢реЗрд╖ рдзреНрд╡рдЬ рд╕реЗрдЯ рдХрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ, рдЬрд┐рд╕реЗ рдлрд┐рд░ рдЕрдкрдбреЗрдЯ рдХреЗ рдЕрдВрдд рдореЗрдВ рд╣рдЯрд╛ рджрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИред рдпрджрд┐ рд╣рдо рдмрд╕ рдПрдХ рд╣реА рдлрд╝рдВрдХреНрд╢рди рдореЗрдВ рдЧрдП, рдФрд░ рдЕрдкрдбреЗрдЯ рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдореЗрдВ рд╣реИ, рддреЛ рд╣рдордиреЗ рдкреВрдВрдЫ рджреНрд╡рд╛рд░рд╛ рдкреБрдирд░рд╛рд╡реГрддреНрддрд┐ рдХреЛ рдкрдХрдбрд╝ рд▓рд┐рдпрд╛ рдФрд░ рд╣рдореЗрдВ рдЗрд╕рдХреЗ рд╕рд╛рде рдХреБрдЫ рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИред рдорд╛рдереЗ рдХрд╛ рд╕рдорд╛рдзрд╛рди рддреБрд░рдВрдд рдбрд┐рдлрд╝реЙрд▓реНрдЯ рдорд╛рди рд╡рд╛рдкрд╕ рдХрд░рдирд╛ рд╣реИред рд╣рд╛рд▓рд╛рдВрдХрд┐, рдпрд╣ рд╕рдмрд╕реЗ рдЕрдЪреНрдЫрд╛ рддрд░реАрдХрд╛ рдирд╣реАрдВ рд╣реИ, рдХреНрдпреЛрдВрдХрд┐ рддрдм рд╕рдВрд╕рд╛рдзрд┐рдд рдореВрд▓реНрдп рдкрд╣рд▓реЗ рдлрд╝рдВрдХреНрд╢рди рдХреЙрд▓ рдкрд░ рд╡рд╛рдкрд╕ рдЖ рдЬрд╛рдПрдЧрд╛ рдФрд░ рдпрд╣ рдЕрдкрдиреЗ рдЖрдк рдХреЗ рдЖрдзрд╛рд░ рдкрд░ рдПрдХ рдорд╛рди рд▓реМрдЯрд╛рдПрдЧрд╛, рдХреЗрд╡рд▓ рдмрд╛рд╣рд░ рд╕реЗ рд╕рдВрд╕рд╛рдзрд┐рдд рдХрд┐рдпрд╛ рдЬрд╛рдПрдЧрд╛ред рд╕рдмрд╕реЗ рдЙрдкрдпреБрдХреНрдд рд╡рд┐рдХрд▓реНрдк рдПрдХ рдЕрдкрд╡рд╛рдж рдХреЛ рдлреЗрдВрдХрдирд╛ рд╣реИ рдЬреЛ рдХреЙрд▓ рд╕реНрдЯреИрдХ рдХреЛ рдкрд┐рдЫрд▓реЗ рдлрд╝рдВрдХреНрд╢рди рдХреЗ "рд╣рд╛рдЗрдкреЛрд╕реНрдЯреИрд╕рд┐рд╕" рдХреЛ рдЕрдирдЗрдВрд╕реНрдЯреЙрд▓ рдХрд░рддрд╛ рд╣реИ рдФрд░ рд╡рд╣рд╛рдВ рд╕реЗ рдбрд┐рдлрд╝реЙрд▓реНрдЯ рдорд╛рди рд▓реМрдЯрд╛рддрд╛ рд╣реИред рдпрд╣рд╛рдВ рдмрддрд╛рдпрд╛ рдЧрдпрд╛ рд╣реИ рдХрд┐ рдпрд╣ рдХреИрд╕реЗ рдХрд╛рдо рдХрд░рддрд╛ рд╣реИ:
public ValueType get()
{
// update() ,
// , get()
// update()
if (updateInProgress)
throw new RecursionDetectedException( this );
// update()
if (isInvalid)
{
// update()
updateInProgress = true ;
try
{
//
value = update();
// isInvalid false update()
//
isInvalid = false ;
}
catch (RecursionDetectedException e)
{
if (e.getRecursionStarter() != this )
throw e; // ,
else
return getDefault(); // -
}
finally
{
// , get()
updateInProgress = false ;
}
}
return value;
}
рд╕рдорд╛рдзрд╛рди рдиреЗ рдПрдХ рдмрдбрд╝реА рдкрд░рд┐рдпреЛрдЬрдирд╛ рдореЗрдВ рдмрд╣реБрдд рд╕рдордп рдмрдЪрд╛рдиреЗ рдХреА рдЕрдиреБрдорддрд┐ рджреАред рдкреНрд░реЛрдЧреНрд░рд╛рдорд░ рдФрд░ рдкреНрд░реЛрд╕реЗрд╕рд░ рджреЛрдиреЛрдВ рдХрд╛ рд╕рдордпред рдкреНрд░рджрд░реНрд╢рди рдХреА рдмрдЪрдд рдпрд╣ рд╣реИ рдХрд┐ рдбреЗрдЯрд╛ рдХреА рдЧрдгрдирд╛ рдХреЗрд╡рд▓ рдорд╛рдВрдЧ рдкрд░ рдХреА рдЬрд╛рддреА рд╣реИ, рдФрд░ рдпрджрд┐ рдЕрдиреБрд░реЛрдз рдирд╣реАрдВ рд╣реБрдЖ рд╣реИ, рддреЛ рдпрд╣ рдбреЗрдЯрд╛ рдХрд┐рд╕реА рдХреЗ рд▓рд┐рдП рдЖрд╡рд╢реНрдпрдХ рд╣реИ рдФрд░ рдЖрдкрдХреЛ рдЗрд╕реЗ рдкрдврд╝рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рдирд╣реАрдВ рд╣реИред рдореБрдЭреЗ рдЙрдореНрдореАрдж рд╣реИ рдХрд┐ рдпреЗ 2 рдЫреЛрдЯреА рдХрдХреНрд╖рд╛рдПрдВ рдЖрдкрдХрд╛ рд╕рдордп рдмрдЪрд╛рдПрдВрдЧреАред рдореБрдЭреЗ рд░рдЪрдирд╛рддреНрдордХ рдЖрд▓реЛрдЪрдирд╛ рдФрд░ рдЙрди рдорд╛рдорд▓реЛрдВ рдореЗрдВ рдЦреБрд╢реА рд╣реЛрдЧреА, рдЬрд┐рдирдореЗрдВ "рдХреБрдЫ рднреА рдХрд╛рдо рдирд╣реАрдВ рдХрд░рддрд╛ рд╣реИред"
рдкреВрд░реНрдг рд╡рд░реНрдЧ рдХреЛрдб:
LazyValue.javaRSLazyValue.java