
XMageã¯ãMagicïŒThe GatheringïŒMTGïŒããã¬ã€ããããã®ã¯ã©ã€ã¢ã³ã/ãµãŒããŒã¢ããªã±ãŒã·ã§ã³ã§ããXMageã¯2010幎ã®åãã«é²åãå§ããŸããããã®éã182ã®ãªãªãŒã¹ããªãªãŒã¹ãããè²¢ç®è ã®è»éå šäœãéãŸãããããžã§ã¯ãã¯çŸåšã掻çºã«éçºãããŠããŸãããã®éçºã«ãåå ããçµ¶å¥œã®æ©äŒã§ãïŒãããã£ãŠã仿¥ãPVS-Studioã®ãŠãã³ãŒã³ã¯XMageã³ãŒãããŒã¹ããã§ãã¯ããŸãã誰ãç¥ã£ãŠããããããã¯æŠéäžã®èª°ããšè¡çªããå¯èœæ§ããããŸãã
ãããžã§ã¯ãã«ã€ããŠç°¡åã«
XMageã¯10幎åããæŽ»çºã«éçºãããŠããŸãããã®ç®æšã¯ããªãªãžãã«ã®MagicïŒTheGatheringã«ãŒãã²ãŒã ã®ç¡æã®ãªãŒãã³ãœãŒã¹ã®ãªã³ã©ã€ã³ããŒãžã§ã³ãäœæããããšã§ãã
ã¢ããªã±ãŒã·ã§ã³ã®æ©èœïŒ
- MTGã®20å¹Žã®æŽå²ã®äžã§çºè¡ãããçŽ19,000æã®ãŠããŒã¯ãªã«ãŒããžã®ã¢ã¯ã»ã¹ã
- ã²ãŒã ã®æ¢åã®ãã¹ãŠã®ã«ãŒã«ã®èªåå¶åŸ¡ãšé©çšã
- ;
- (AI);
- (Standard, Modern, Vintage, Commander );
- , .
Delft University of Technology 2018ïŒãœãããŠã§ã¢ã¢ãŒããã¯ãã£ã®ä¿®å£«å·ïŒã®åŠç ã®ä»äºã«åºããããŸãããããã¯ã圌ãããªãŒãã³ãœãŒã¹ãããžã§ã¯ãã«ç©æ¥µçã«åå ãããšããäºå®ããæãç«ã£ãŠããŸãããããã¯éåžžã«è€éã§ç©æ¥µçã«éçºãããªããã°ãªããŸããã§ãããåŠçã¯8é±éã«ããã£ãŠãéžæãããœãããŠã§ã¢ã®ã¢ãŒããã¯ãã£ãçè§£ããŠèª¬æããããã«ãã³ãŒã¹ãšãªãŒãã³ãœãŒã¹ãããžã§ã¯ããç ç©¶ããŸããã 以äžã§ãããã®äœæ¥ã§ã¯ãXMageãããžã§ã¯ããåæããSonarQubeã䜿çšããŠããŸããŸãªã¡ããªãã¯ïŒã³ãŒãã®è¡æ°ããµã€ã¯ãããã£ãã¯ãªè€éããã³ãŒãã®éè€ãã³ãŒãã®èãããšã©ãŒãè匱æ§ãªã©ïŒãååŸããããšãè¡ããŸããã
ç§ã®æ³šæã¯ã2018å¹Žã®æç¹ã§SonarQubeã¹ãã£ã³ã1,000,000è¡ã®ã³ãŒãããã700ã®æ¬ é¥ïŒãã°ãè匱æ§ïŒã瀺ãããšããäºå®ã«æ¹ãããŸããã
å¯çš¿è ã®æŽå²ãæãäžãããšãããåãåã£ãèŠåä»ãã®ã¬ããŒããããããããã«ãŒããŸãã¯ãã¯ãªãã£ã«ã«ãã«ããŽãªããçŽ30åã®æ¬ é¥ãä¿®æ£ããããã«ãã«ãªã¯ãšã¹ããè¡ã£ãããšãããããŸãããæ®ãã®èŠåã«ã€ããŠã¯äžæã§ãããèŠéãããŠããªãããšãé¡ã£ãŠããŸãã
ãããã2幎ãçµã¡ãã³ãŒãããŒã¹ã¯çŽ250,000è¡ã®ã³ãŒãã§æé·ããŸãããããã¯ãç¶æ³ãã©ããªã£ãŠããã®ãã確èªããã®ã«ååãªçç±ã§ãã
åæã«ã€ããŠ
åæã®ããã«ãXMageãªãªãŒã¹-1.4.44V0ã䜿çšããŸããã
ç§ã¯ãã®ãããžã§ã¯ãã«ãšãŠã幞éã§ãããMavenã䜿çšããXMageã®æ§ç¯ã¯ãéåžžã«ç°¡åã§ããããšã倿ããŸããïŒããã¥ã¡ã³ãã«èšèŒãããŠãããšããïŒã
mvn clean install -DskipTests
ç§ã«ã¯ãã以äžäœãå¿ èŠãããŸããã§ãããæ¶ŒããïŒ
PVS-Studioãã©ã°ã€ã³ã®Mavenãžã®çµ±åã«ãåé¡ã¯ãããŸããã§ããããã¹ãŠãããã¥ã¡ã³ãã®ãšããã§ãã
åæåŸã911ã®èŠåãåä¿¡ããããã®ãã¡674ã¯1ããã³2ã®ä¿¡é Œã¬ãã«ã®èŠåã«å¯Ÿãããã®ã§ãããéåžžã誀æ€ç¥ã®å²åãé«ãããããã®èšäºã§ã¯ã¬ãã«3ã®èŠåã«ã€ããŠã¯èæ ®ããŠããŸãããå®éã®æŠéã§éçã¢ãã©ã€ã¶ãŒã䜿çšããå Žåãã³ãŒãã®éå€§ãªæ¬ é¥ã瀺ããŠããå¯èœæ§ãããããããã®ãããªèŠåãç¡èŠããããšã¯ã§ããªããšããäºå®ã«æ³šæãåããããšæããŸãã
ããã«ãããã€ãã®ã«ãŒã«ã®èŠåã¯ãç§ããããããžã§ã¯ãã«ç²ŸéããŠãã人ã«ããèæ ®ãããŠãããšããçç±ã§ãèæ ®ããŸããã§ããã
- V6022, /. 336 .
- V6014, , . 73 .
- V6021, , . 36 .
- V6048, , . 17 .
ããã«ãããã€ãã®èšºæã«ãŒã«ã«ãããåãã¿ã€ãã®æãããªèª€æ€ç¥ãçŽ20ä»¶çºçããŸãããtodoã«åé²ïŒ
ãã®çµæããã¹ãŠãå·®ãåŒããšãçŽ190ã®ããžãã£ããæ€èšã®ããã«ç§ã«å±ããŸããã
ããªã¬ãŒã確èªããŠãããšãã«ãåãã¿ã€ãã®å€ãã®å°ããªæ¬ é¥ãç¹å®ãããŸããããããã¯ããããã°ãŸãã¯ç¡æå³ãªãã§ãã¯ãŸãã¯æäœã«é¢é£ããŠããŸããããŸããå€ãã®ããžãã£ããªç¹ã¯ããªãã¡ã¯ã¿ãªã³ã°ãæé¡ããéåžžã«å¥åŠãªã³ãŒãã«é¢é£ããŠããŸããã
ãã®çµæããã®èšäºã§ã¯ã11ã®èšºæã«ãŒã«ãç¹å®ããæãè峿·±ãããªã¬ãŒã®1ã€ãåæããŸããã
äœãèµ·ãã£ãã®ãèŠãŠã¿ãŸãããã
èŠåN1
V6003'ifïŒcardïŒ= NullïŒ{...} else ifïŒcardïŒ= NullïŒ{...} 'ãã¿ãŒã³ã®äœ¿çšãæ€åºãããŸãããè«çãšã©ãŒãååšããå¯èœæ§ããããŸããTorrentialGearhulk.javaïŒ90ïŒãTorrentialGearhulk.javaïŒ102ïŒ
@Override
public boolean apply(Game game, Ability source) {
....
Card card = game.getCard(....);
if (card != null) {
....
} else if (card != null) {
....
}
....
}
ããã§ã¯ãã¹ãŠãåçŽã§ããããã°ã©ã ããã®ãã€ã³ãã«å°éããªãããcardïŒ= Nullãåžžã«falseã«ãªããããif-else-ifæ§æã®2çªç®ã®æ¡ä»¶ã¹ããŒãã¡ã³ãifïŒcardïŒ= NullïŒã®æ¬äœã¯å®è¡ãããŸããã
èŠåN2
V6004ãthenãã¹ããŒãã¡ã³ãã¯ãelseãã¹ããŒãã¡ã³ããšåçã§ããAsThoughEffectImpl.javaïŒ35ïŒãAsThoughEffectImpl.javaïŒ37ïŒ
@Override
public boolean applies(....) {
// affectedControllerId = player to check
if (getAsThoughEffectType().equals(AsThoughEffectType.LOOK_AT_FACE_DOWN)) {
return applies(objectId, source, playerId, game);
} else {
return applies(objectId, source, playerId, game);
}
}
ãªãŒãã³ãœãŒã¹ãããžã§ã¯ãããã§ãã¯ããç§ã®ç·Žç¿ã§ãã°ãã°çºçãããããµããééããã³ããŒããŒã¹ãïŒãããšãç§ã¯äœããè¶³ããªãã®ã§ããïŒelseãã©ã³ãã§falseãè¿ãå¿ èŠããããšä»®å®ããŸãã
PSã©ã¡ãããšããã°ããããã¯ç°ãªãã¡ãœããã§ãããããååž°åŒã³åºãã¯é©çšãããŸããïŒ....ïŒã
åæ§ã®ããªã¬ãŒïŒ
- V6004ãthenãã¹ããŒãã¡ã³ãã¯ãelseãã¹ããŒãã¡ã³ããšåçã§ããGuiDisplayUtil.javaïŒ194ïŒãGuiDisplayUtil.javaïŒ198ïŒ
èŠåN3
V6007åŒ 'filter.getMessageïŒïŒãToLowerCaseïŒLocale.ENGLISHïŒ.startsWithïŒ "Each"ïŒ'ã¯åžžã«falseã§ããSetPowerToughnessAllEffect.javaïŒ107ïŒ
@Override
public String getText(Mode mode) {
StringBuilder sb = new StringBuilder();
....
if (filter.getMessage().toLowerCase(Locale.ENGLISH).startsWith("Each ")) {
sb.append(" has base power and toughness ");
} else {
sb.append(" have base power and toughness ");
}
....
return sb.toString();
}
V6007 蚺æã«ãŒã«ããªã¬ãŒã¯ããã§ãã¯ããããã¹ãŠã®ãããžã§ã¯ãã§éåžžã«äººæ°ããããŸãã XMageãäŸå€ã§ã¯ãããŸããïŒ79åïŒãã«ãŒã«ã®æœè¡ã¯ãååãšããŠãã¹ãŠãã±ãŒã¹ã«ãããŸãããå€ãã®ã±ãŒã¹ã¯ãããã°ã次ã«åä¿éºããããŠä»ã®äœãã«åœãŠã¯ãŸããŸããäžè¬ã«ãã³ãŒãã®äœæè ã¯ãç§ããããã®ãããªããžãã£ããªç¹ãç£èŠããæ¹ãé©åã§ãã
ãã ãããã®ããªã¬ãŒã¯ééããªããšã©ãŒã§ããè¡ã®å é ã«å¿ããŠfilter.getMessageïŒïŒããsbãhas ...ããŸãã¯ãhave ...ããšããããã¹ãã远å ãããŸããããããééãã¯ãéçºè ãæååã倧æåã§å§ãŸãããšã確èªãããã®åã«ãã®åãæååãå°æåã«å€æããããšã§ãããã£ãšããã®çµæã远å ãããè¡ã¯åžžã«ãhave ...ãã«ãªããŸããæ¬ é¥ã®çµæã¯é倧ã§ã¯ãããŸããããäžå¿«ã§ããããŸããæåéãã«æ§æãããŠããªãããã¹ããã©ããã«è¡šç€ºãããŸãã
ç§ãæãè峿·±ããšæã£ãããªã¬ãŒïŒ
- V6007åŒ 't.startsWithïŒ "-"ïŒ'ã¯åžžã«falseã§ããBoostSourceEffect.javaïŒ103ïŒ
- V6007åŒ 'setNames.isEmptyïŒïŒ'ã¯åžžã«falseã§ããDownloadPicturesService.javaïŒ300ïŒ
- V6007åŒ 'existingBucketName == null'ã¯åžžã«falseã§ããS3Uploader.javaïŒ23ïŒ
- V6007åŒ 'ïŒLastRule.endsWithïŒ "ã"ïŒ'ã¯åžžã«trueã§ããEffects.javaïŒ76ïŒ
- V6007åŒ 'subtypesToIgnore :: contains'ã¯åžžã«falseã§ããVerificationCardDataTest.javaïŒ893ïŒ
- V6007åŒ 'notStartedTables == 1'ã¯åžžã«falseã§ããMageServerImpl.javaïŒ1330ïŒ
èŠåN4
V6008ãsavedSpecialRaresãã®ãã«éåç §ãDragonsMaze.javaïŒ230ïŒ
public final class DragonsMaze extends ExpansionSet {
....
private List<CardInfo> savedSpecialRares = new ArrayList<>();
....
@Override
public List<CardInfo> getSpecialRare() {
if (savedSpecialRares == null) { // <=
CardCriteria criteria = new CardCriteria();
criteria.setCodes("GTC").name("Breeding Pool");
savedSpecialRares.addAll(....); // <=
criteria = new CardCriteria();
criteria.setCodes("GTC").name("Godless Shrine");
savedSpecialRares.addAll(....);
....
}
return new ArrayList<>(savedSpecialRares);
}
}
ããŒãµãŒã¯ãå®è¡ãã³ã¬ã¯ã·ã§ã³ã®æåã®å ¥åã«éãããšãã«ãnullåç §savedSpecialRaresã®åç §ãè§£é€ããããšã«ã€ããŠæå¥ãèšããŸãã
æåã«é ã«æµ®ãã¶ã®ã¯ãsavedSpecialRares == nullãšsavedSpecialRaresïŒ= NullãåçŽã«æ··åããããšã§ãããã ãããã®ãããªå ŽåãsavedSpecialRares == nullãåŒãç¶ãå¯èœã§ãããããã³ã¬ã¯ã·ã§ã³ãã¡ãœããããè¿ããããšãã«ArrayListã®ã³ã³ã¹ãã©ã¯ã¿ãŒã§NPEãçºçããå¯èœæ§ããããŸããé ã«æµ®ãã¶æåã®è§£æ±ºçã§ã³ãŒããä¿®æ£ããããšã¯è¯ãéžæè¢ã§ã¯ãããŸãããã³ãŒããå°ãçè§£ããåŸãs avedSpecialRaresã¯ã宣èšããããšããã«ç©ºã®ã³ã¬ã¯ã·ã§ã³ã«ãã£ãŠå®çŸ©ãããä»ã®å Žæã«åå²ãåœãŠãããªãããšãããããŸãããããã¯ç§ãã¡ã«ãããäŒããŸãsavedSpecialRaresãnullã«ãªãããšã¯ãªããã³ã¬ã¯ã·ã§ã³ã«å°éããããšã¯ãªããããã¢ãã©ã€ã¶ãŒãèŠåããnullåç §ã®éåç §ã¯çºçããŸããããã®çµæãã¡ãœããã¯åžžã«ç©ºã®ã³ã¬ã¯ã·ã§ã³ãè¿ããŸãã
PSãããä¿®æ£ããã«ã¯ãsavedSpecialRares == nullãsavedSpecialRares.isEmptyïŒïŒã«çœ®ãæããå¿ èŠããããŸãã
PPSæ®å¿µãªãããXMageããã¬ã€ããŠããéã¯ãDragon'sMazeã³ã¬ã¯ã·ã§ã³ã®ç¹å¥ãªã¬ã¢ã«ãŒããå ¥æããããšã¯ã§ããŸããã
nullåç §ãéåç §ããå¥ã®ã±ãŒã¹ïŒ
- V6008ãäžèŽãã®ãã«éåç §ãTableController.javaïŒ973ïŒ
èŠåN5
V6012 'ïŒïŒ'æŒç®åã¯ããã®æ¡ä»¶åŒã«é¢ä¿ãªããåžžã«1ã€ã®åãå€ 'table.getCreateTimeïŒïŒ'ãè¿ããŸããTableManager.javaïŒ418ïŒãTableManager.javaïŒ418ïŒ
private void checkTableHealthState() {
....
logger.debug(.... + formatter.format(table.getStartTime() == null
? table.getCreateTime()
: table.getCreateTime()) + ....);
....
}
ããã§ã3倿Œç®åïŒïŒæ¡ä»¶table.getStartTimeïŒïŒ== nullã«é¢ä¿ãªãåãå€ãè¿ããŸããã³ãŒãã®å®æã¯éçºè ã«æ®é ·ãªåè«ãèšã£ããšæããŸããä¿®æ£ãªãã·ã§ã³ïŒ
private void checkTableHealthState() {
....
logger.debug(.... + formatter.format(table.getStartTime() == null
? table.getCreateTime()
: table.getStartTime()) + ....);
....
}
èŠåN6
V6026ãã®å€ã¯ããthis.loseOtherã倿°ã«ãã§ã«å²ãåœãŠãããŠããŸããGetsCreatureTypeTargetEffect.javaïŒ54ïŒ
public
BecomesCreatureTypeTargetEffect(final BecomesCreatureTypeTargetEffect effect) {
super(effect);
this.subtypes.addAll(effect.subtypes);
this.loseOther = effect.loseOther;
this.loseOther = effect.loseOther;
}
å²ãåœãŠæååãéè€ããŠããŸããéçºè ããããããŒã䜿çšããŠå°ã倢äžã«ãªããæ°ã¥ããªãã£ãããã§ãããããããšãã§ã¯ãã«ã¯å€æ°ã®ãã£ãŒã«ããããããšãèãããšããã©ã°ã¡ã³ãã«çŠç¹ãåœãŠã䟡å€ããããŸãã
èŠåN7
V6036ãªãã·ã§ã³ã®åæåãããŠããªã 'selectUser'ã®å€ã䜿çšãããŸããSession.javaïŒ227ïŒ
public String connectUserHandling(String userName, String password)
{
....
if (!selectUser.isPresent()) { // user already exists
selectUser = UserManager.instance.getUserByName(userName);
if (selectUser.isPresent()) {
User user = selectUser.get();
....
}
}
User user = selectUser.get(); // <=
....
}
ã¢ãã©ã€ã¶ãŒã®èŠåãããselectUser.getïŒïŒãNoSuchElementExceptionãã¹ããŒããå¯èœæ§ããããšçµè«ä»ããããšãã§ããŸãã
ããã§äœãèµ·ãã£ãŠããã®ãã詳ããèŠãŠã¿ãŸãããããŠãŒã¶ãŒããã§ã«ååšãã
ãšããã³ã¡ã³ããä¿¡ããå ŽåãäŸå€ã¯ã¹ããŒãããŸããã
....
if (!selectUser.isPresent()) { // user already exists
....
}
User user = selectUser.get()
....
ãã®å Žåãããã°ã©ã ã®å®è¡ã¯æ¡ä»¶ä»ãã¹ããŒãã¡ã³ãã®æ¬äœã«ã¯å ¥ããŸããããããŠããã¹ãŠã倧äžå€«ã«ãªããŸããããããçåãçããŸããå®è¡ãããªãã®ã«ããªãè€éãªããžãã¯ãæã€æ¡ä»¶ä»ãæŒç®åãå¿ èŠãªã®ã§ããïŒ
ããããã³ã¡ã³ããäœããªãå Žåã¯ã©ããªããŸããïŒ
....
if (!selectUser.isPresent()) { // user already exists
selectUser = UserManager.instance.getUserByName(userName);
if (selectUser.isPresent()) {
....
}
}
User user = selectUser.get(); // <=
....
次ã«ãå®è¡ã¯æ¡ä»¶ã¹ããŒãã¡ã³ãã®æ¬äœã«å ¥ããgetUserByNameïŒïŒãä»ããŠãŠãŒã¶ãŒãåååŸããŸãããŠãŒã¶ãŒã®æå¹æ§ãå床ãã§ãã¯ãããŸããããã¯ãselectUserãåæåãããŠããªãå¯èœæ§ãããããšã瀺ããŠããŸãããã®å Žåãä»ã«ãã©ã³ãã¯ãããŸãããããã«ãããåé¡ã®ã³ãŒãè¡ã§NoSuchElementExceptionãçºçããŸãã
èŠåN8
V6042åŒã¯ã¿ã€ããAããšã®äºææ§ããã§ãã¯ãããŸãããã¿ã€ããBãã«ãã£ã¹ããããŸãã CheckBoxList.javaïŒ586ïŒ
/**
* sets the model - must be an instance of CheckBoxListModel
*
* @param model the model to use
* @throws IllegalArgumentException if the model is not an instance of
* CheckBoxListModel
* @see CheckBoxListModel
*/
@Override
public void setModel(ListModel model) {
if (!(model instanceof CheckBoxListModel)) {
if (model instanceof javax.swing.DefaultListModel) {
super.setModel((CheckBoxListModel)model); // <=
}
else {
throw new IllegalArgumentException(
"Model must be an instance of CheckBoxListModel!");
}
}
else {
super.setModel(model);
}
}
ã³ãŒãã®äœæè ã¯ãããã§äœãã«ã€ããŠæ··ä¹±ããŠããŸããæåã«ãã¢ãã«ãCheckBoxListModelã§ãªãããšã確èªãããã®çµæããªããžã§ã¯ãããã®ã¿ã€ãã«æç€ºçã«ãã£ã¹ãããŸãããã®ãããsetModelã¡ãœããã¯ãããã«å°éãããšããã«ClassCastExceptionãã¹ããŒããŸããCheckBoxList.java
ãã¡ã€ã«ã¯2幎åã«è¿œå ããããã®ãã°ã¯ãã以æ¥ã³ãŒãã«æ®ã£ãŠããŸããã©ããããééã£ããã©ã¡ãŒã¿ã®ãã¹ãã¯ãªããäžé©åãªã¿ã€ãã®ãªããžã§ã¯ãã§ãã®ã¡ãœãããå®éã«äœ¿çšããããšã¯ãªãã®ã§ãããã¯çããŠããŸãã çªç¶èª°ãããã®ã¡ãœããã«æ¥ç¶ããŠJavadocãèªã¿åããšãClassCastExceptionã§ã¯ãªãIllegalArgumentExceptionãçºçããããšãäºæ³ãããŸãã
..ãæå³çã«ãã®äŸå€ã«ééãã人ã¯ããªããšæããŸããã誰ãç¥ã£ãŠããŸããã
ããã¥ã¡ã³ããèãããšãã³ãŒãã¯ããããæ¬¡ã®ããã«ãªããŸãã
public void setModel(ListModel model) {
if (!(model instanceof CheckBoxListModel)) {
throw new IllegalArgumentException(
"Model must be an instance of CheckBoxListModel!");
}
else {
super.setModel(model);
}
}
èŠåN9
V6060ããã¬ãŒã€ãŒãåç §ã¯ãnullã«å¯ŸããŠæ€èšŒãããåã«äœ¿çšãããŸãããVigeanIntuition.javaïŒ79ïŒãVigeanIntuition.javaïŒ78ââïŒ
@Override
public boolean apply(Game game, Ability source) {
MageObject sourceObject = game.getObject(source.getSourceId());
Player player = game.getPlayer(source.getControllerId());
Library library = player.getLibrary(); // <=
if (player != null && sourceObject != null && library != null) { // <=
....
}
}
V6060ã¯ããªããžã§ã¯ããnullã§ãããã©ããããã§ãã¯ãããåã«ããªããžã§ã¯ããã¢ã¯ã»ã¹ãããŠããããšãéçºè ã«èŠåããŸãããã®ã«ãŒã«ã®ããªã¬ãŒã¯ããªãŒãã³ãœãŒã¹ãããžã§ã¯ãã®ãã§ãã¯ã«é¢ããèšäºã«ããèŠãããŸããéåžžããã®çç±ã¯ããªãã¡ã¯ã¿ãªã³ã°ã®å€±æãŸãã¯ã¡ãœããã®å¥çŽã®å€æŽã§ããgetPlayerïŒïŒã¡ãœããã®å®£èšã«æ³šæãæããšããã¹ãŠãããã«å®è¡ãããŸãã
// Result must be checked for null.
// Possible errors search pattern: (\S*) = game.getPlayer.+\n(?!.+\1 != null)
Player getPlayer(UUID playerId);
èŠåN10
V60722ã€ã®é¡äŒŒããã³ãŒããã©ã°ã¡ã³ããèŠã€ãããŸããããããããããã¯ã¿ã€ããã¹ã§ããããplayerAãã®ä»£ããã«ãplayerBã倿°ã䜿çšããå¿ èŠããããŸãã SubTypeChangingEffectsTest.javaïŒ162ïŒãSubTypeChangingEffectsTest.javaïŒ158ïŒãSubTypeChangingEffectsTest.javaïŒ156ïŒãSubTypeChangingEffectsTest.javaïŒ160ïŒ
@Test
public void testArcaneAdaptationGiveType() {
addCard(Zone.HAND, playerA, "Arcane Adaptation", 1); // Enchantment {2}{U}
addCard(Zone.BATTLEFIELD, playerA, "Island", 3);
addCard(Zone.HAND, playerA, "Silvercoat Lion");
addCard(Zone.BATTLEFIELD, playerA, "Silvercoat Lion");
addCard(Zone.GRAVEYARD, playerA, "Silvercoat Lion"); // <=
addCard(Zone.HAND, playerB, "Silvercoat Lion");
addCard(Zone.BATTLEFIELD, playerB, "Silvercoat Lion");
addCard(Zone.GRAVEYARD, playerA, "Silvercoat Lion"); // <=
....
for (Card card : playerB.getGraveyard().getCards(currentGame)) {
if (card.isCreature()) {
Assert.assertEquals(card.getName() + " should not have ORC type",
false, card.getSubtype(currentGame).contains(SubType.ORC));
Assert.assertEquals(card.getName() + " should have CAT type",
true, card.getSubtype(currentGame).contains(SubType.CAT));
}
}
}
ãã®ãšã©ãŒããã¹ãã«ããããšã確èªããããããŸãããããã¯ãã¹ãã§ãããšèããŠãèŠã€ãã£ãæ¬ é¥ã®äŸ¡å€ãããã«äžããããšãã§ããŸãããããããªããç§ã¯ããªãã«åæããŸãããçµå±ã®ãšããããã¹ãã¯éçºã«ãããŠããªãéèŠãªåœ¹å²ãæããïŒããã°ã©ãã³ã°ã»ã©ç®ç«ããªããã®ã®ïŒããªãªãŒã¹ã«æ¬ é¥ãçŸãããšãããã«ãã¹ã/ãã¹ã¿ãŒã«ââæãåãå§ããŸãããããã£ãŠãæ¬ é¥ã®ãããã¹ãã¯åãå ¥ããããŸãããã§ã¯ããªããã®ãããªãã¹ããå¿ èŠãªã®ã§ããïŒãªããããã«ãªãœãŒã¹ã浪費ããã®ã§ããïŒtestArcaneAdaptationGiveTypeïŒïŒ
ã¡ãœããã¯ããArcaneAdaptationãã«ãŒãããã¹ãããŸããåãã¬ã€ã€ãŒã«ã¯ãç¹å®ã®ãã¬ã€ãšãªã¢ã«ã«ãŒããé ãããŸãããããŠãã³ããŒïŒããŒã¹ãã®ãããã§ãplayerAã¯ãCemeteryããã¬ã€ãšãªã¢ã§2æã®åäžã®ãSilvercoatLionãã«ãŒããæã«å ¥ããŸãããã ããäœãåŸãããªãã£ããæ¬¡ã«ãããã€ãã®éæ³ãšããèªäœããã¹ãããŸããçŸåšã®å³é¢ã®playerBã®
ãå¢å°ãã«ãã¹ããæ¥ããšããå¢å°ãã«ã¯äœããªãã£ãããããã¹ãã®å®è¡ãã«ãŒãã«å ¥ãããšã¯ãããŸãããããã¯ããã¹ããéå§ãããšãã«å€ãè¯ãSystem.out.printlnïŒïŒã§èŠã€ããŸããã ä¿®æ£ãããã³ããŒïŒããŒã¹ãïŒ
....
addCard(Zone.HAND, playerA, "Silvercoat Lion");
addCard(Zone.BATTLEFIELD, playerA, "Silvercoat Lion");
addCard(Zone.GRAVEYARD, playerA, "Silvercoat Lion"); // <=
addCard(Zone.HAND, playerB, "Silvercoat Lion");
addCard(Zone.BATTLEFIELD, playerB, "Silvercoat Lion");
addCard(Zone.GRAVEYARD, playerB, "Silvercoat Lion"); // <=
....
ã³ãŒãã埮調æŽããåŸããã¹ããå®è¡ãããšãplayerBã®å¢å°ã«ããã¯ãªãŒãã£ãŒã®ãã§ãã¯ãæ©èœãå§ããŸãããã¢ããã¥ãŒãSystem.out.printlnïŒïŒïŒ
ä¿®æ£åãšä¿®æ£åŸã®äž¡æ¹ã§ãã¹ããç·è²ã«ãªãã幞éã§ããããããããã°ã©ã å®è¡ã®ããžãã¯ã倿Žããç·šéã®å Žåããã®ãããªãã¹ãã¯ããªãã«äžå©çãããããããšã©ãŒããã£ããšããŠãæ£åžžã«å®äºããããšãéç¥ããŸãã
åãã³ããŒ-ä»ã®å Žæã«è²Œãä»ããŸãïŒ
- V60722ã€ã®é¡äŒŒããã³ãŒããã©ã°ã¡ã³ããèŠã€ãããŸããããããããããã¯ã¿ã€ããã¹ã§ããããplayerAãã®ä»£ããã«ãplayerBã倿°ã䜿çšããå¿ èŠããããŸããPaintersServantTest.javaïŒ33ïŒãPaintersServantTest.javaïŒ29ïŒãPaintersServantTest.javaïŒ27ïŒãPaintersServantTest.javaïŒ31ïŒ
- V60722ã€ã®é¡äŒŒããã³ãŒããã©ã°ã¡ã³ããèŠã€ãããŸããããããããããã¯ã¿ã€ããã¹ã§ããããplayerAãã®ä»£ããã«ãplayerBã倿°ã䜿çšããå¿ èŠããããŸããSubTypeChangingEffectsTest.javaïŒ32ïŒãSubTypeChangingEffectsTest.javaïŒ28ïŒãSubTypeChangingEffectsTest.javaïŒ26ïŒãSubTypeChangingEffectsTest.javaïŒ30ïŒ
èŠåN11
V6086çãããã³ãŒãã®ãã©ãŒãããã'else'ããŒã¯ãŒããæ¬ èœããŠããå¯èœæ§ããããŸããDeckImporter.javaïŒ23ïŒ
public static DeckImporter getDeckImporter(String file) {
if (file == null) {
return null;
} if (file.toLowerCase(Locale.ENGLISH).endsWith("dec")) { // <=
return new DecDeckImporter();
} else if (file.toLowerCase(Locale.ENGLISH).endsWith("mwdeck")) {
return new MWSDeckImporter();
} else if (file.toLowerCase(Locale.ENGLISH).endsWith("txt")) {
return new TxtDeckImporter(haveSideboardSection(file));
}
....
else {
return null;
}
}
蚺æã«ãŒã«V6086ã¯ã誀ã£ãif-else-ifãã©ãŒãããã蚺æããelseã®çç¥ãæå³ããŸãã
ãã®ã³ãŒãã¹ããããã¯ããã瀺ããŠããŸãããã®å ŽåãnullåŒãè¿ãããããããã©ãŒããããäžæ£ç¢ºã§ãã£ãŠãäœãèµ·ãããŸãããããã®ãããªã±ãŒã¹ãèŠã€ããå¿ èŠã¯ãªãã®ã§ãèŠã€ããã®ã¯ãã°ãããããšã§ããelseã
çç¥ãããšãäºæããªãåäœãçºçããå¯èœæ§ãããå ŽåãèããŠã¿ãŸãããã
public SomeType smtMethod(SomeType obj) {
....
if (obj == null) {
obj = getNewObject();
} if (obj.isSomeObject()) {
// some logic
} else if (obj.isOtherSomething()) {
obj = calulateNewObject(obj);
// some logic
}
....
else {
// some logic
}
return obj;
}
ããã§ãobj == nullã®å Žåãåé¡ã®ãªããžã§ã¯ãã«ã¯äœããã®å€ãå²ãåœãŠãããelseãæ¬ èœããŠãããšãæ°ããå²ãåœãŠããããªããžã§ã¯ããif-else-ifãã§ãŒã³ã«æ²¿ã£ãŠãã§ãã¯ããå§ããŸããããªããžã§ã¯ãã¯ããã«æ¹æ³ã
çµè«
XMageã®ãã§ãã¯ã¯ãææ°ã®éçã¢ãã©ã€ã¶ãŒã®æ©èœãæããã«ããå¥ã®èšäºã§ããçŸä»£ã®éçºã§ã¯ããœãããŠã§ã¢ã®è€éããå¢ãã«ã€ããŠããããã®å¿ èŠæ§ã¯é«ãŸãã ãã§ãããŸãããªãªãŒã¹ããã¹ãããŠãŒã¶ãŒãã£ãŒãããã¯ã®æ°ã«é¢ä¿ãªãããã°ã¯åžžã«ã³ãŒãããŒã¹ã«äŸµå ¥ããããã®æã穎ãèŠã€ããŸããã§ã¯ãé²åŸ¡ã«å¥ã®éå£ã远å ããŠã¿ãŸãããïŒ
ãåç¥ã®ããã«ãã¢ãã©ã€ã¶ãŒã¯èª€æ€ç¥ãèµ·ãããããåŸåããããŸãïŒPVS-Studio Javaãå«ãïŒãããã¯ãæãããªæ¬ é¥ãšæ··ä¹±ããããã³ãŒãã®äž¡æ¹ã®çµæã§ããå¯èœæ§ããããŸãïŒãããã¢ãã©ã€ã¶ãŒã¯ãããçè§£ããŸããã§ããïŒãããªãã¯ããããçè§£ããŠæ±ããããããããšãªãããã«éäŒããå¿ èŠããããŸããã誀æ€ç¥ããããã®ä¿®æ£ãåŸ ã£ãŠããéãããªãã¯ããããã®æ¹æ³ã䜿çšããããšãã§ããŸãèŠåãæå¶ããŸãã
çµè«ãšããŠãç§ãã¡ã®ãŠã§ããµã€ãããã¢ãã©ã€ã¶ãŒãããŠã³ããŒãããŠãå人çã«ã¢ãã©ã€ã¶ãŒã«ãè§Šãããããšããå§ãããŸãã

ãã®èšäºãè±èªã話ãèŽè¡ãšå ±æãããå Žåã¯ã翻蚳ãªã³ã¯ã䜿çšããŠãã ããïŒããã·ã ã¹ããã¡ãããXMageã®ã³ãŒãã確èªãããã©ãŽã³ã®è¿·è·¯ã³ã¬ã¯ã·ã§ã³ã®ç¹å¥ãªã¬ã¢ã«ãŒããå ¥æã§ããªãçç±ã