package repository import ( "errors" "fmt" "joylink.club/rtsssimulation/repository/model/proto" ) type Repository struct { id string version string physicalSectionMap map[string]*PhysicalSection checkPointMap map[string]*CheckPoint turnoutMap map[string]*Turnout signalMap map[string]*Signal responderMap map[string]*Transponder slopeMap map[string]*Slope sectionalCurvatureMap map[string]*SectionalCurvature kilometerConvertMap map[string]*proto.KilometerConvert relayMap map[string]*Relay phaseFailureProtectorMap map[string]*PhaseFailureProtector buttonMap map[string]*Button linkMap map[string]*Link } func newRepository(id string, version string) *Repository { return &Repository{ id: id, version: version, physicalSectionMap: make(map[string]*PhysicalSection), checkPointMap: make(map[string]*CheckPoint), turnoutMap: make(map[string]*Turnout), signalMap: make(map[string]*Signal), responderMap: make(map[string]*Transponder), slopeMap: make(map[string]*Slope), sectionalCurvatureMap: make(map[string]*SectionalCurvature), kilometerConvertMap: make(map[string]*proto.KilometerConvert), relayMap: make(map[string]*Relay), phaseFailureProtectorMap: make(map[string]*PhaseFailureProtector), linkMap: make(map[string]*Link), buttonMap: make(map[string]*Button), } } // FindById 根据模型的复合id获取模型数据 func (repo *Repository) FindById(id string) Identity { if md, ok := repo.turnoutMap[id]; ok { return md } if md, ok := repo.signalMap[id]; ok { return md } if md, ok := repo.relayMap[id]; ok { return md } return nil } func (repo *Repository) PhysicalSectionList() []*PhysicalSection { var list []*PhysicalSection for _, model := range repo.physicalSectionMap { list = append(list, model) } return list } func (repo *Repository) CheckPointList() []*CheckPoint { var list []*CheckPoint for _, model := range repo.checkPointMap { list = append(list, model) } return list } func (repo *Repository) TurnoutList() []*Turnout { var list []*Turnout for _, model := range repo.turnoutMap { list = append(list, model) } return list } func (repo *Repository) SignalList() []*Signal { var list []*Signal for _, model := range repo.signalMap { list = append(list, model) } return list } func (repo *Repository) ResponderList() []*Transponder { var list []*Transponder for _, model := range repo.responderMap { list = append(list, model) } return list } func (repo *Repository) SlopeList() []*Slope { var list []*Slope for _, model := range repo.slopeMap { list = append(list, model) } return list } func (repo *Repository) SectionalCurvatureList() []*SectionalCurvature { var list []*SectionalCurvature for _, model := range repo.sectionalCurvatureMap { list = append(list, model) } return list } func (repo *Repository) LinkList() []*Link { var list []*Link for _, model := range repo.linkMap { list = append(list, model) } return list } func (repo *Repository) KilometerConvertList() []*proto.KilometerConvert { var list []*proto.KilometerConvert for _, model := range repo.kilometerConvertMap { list = append(list, model) } return list } func (repo *Repository) RelayList() []*Relay { var list []*Relay for _, model := range repo.relayMap { list = append(list, model) } return list } func (repo *Repository) ButtonList() []*Button { var list []*Button for _, model := range repo.buttonMap { list = append(list, model) } return list } func (repo *Repository) FindModel(deviceId string, deviceType proto.DeviceType) (Identity, error) { switch deviceType { case proto.DeviceType_DeviceType_PhysicalSection: return repo.physicalSectionMap[deviceId], nil case proto.DeviceType_DeviceType_CheckPoint: return repo.checkPointMap[deviceId], nil case proto.DeviceType_DeviceType_Turnout: return repo.turnoutMap[deviceId], nil case proto.DeviceType_DeviceType_Signal: return repo.signalMap[deviceId], nil case proto.DeviceType_DeviceType_Transponder: return repo.responderMap[deviceId], nil case proto.DeviceType_DeviceType_Slope: return repo.slopeMap[deviceId], nil case proto.DeviceType_DeviceType_SectionalCurvature: return repo.sectionalCurvatureMap[deviceId], nil case proto.DeviceType_DeviceType_Link: return repo.linkMap[deviceId], nil default: return nil, errors.New(fmt.Sprintf("仓库中不存在[%s]类型的模型", deviceType)) } } func (repo *Repository) FindLink(id string) *Link { return repo.linkMap[id] } func (repo *Repository) FindTurnout(id string) *Turnout { return repo.turnoutMap[id] } func (repo *Repository) FindPhysicalSection(id string) *PhysicalSection { return repo.physicalSectionMap[id] } func (repo *Repository) AddPhysicalSection(section *PhysicalSection) { repo.physicalSectionMap[section.Id()] = section } func (repo *Repository) ConvertKilometer(km *proto.Kilometer, cs string) *proto.Kilometer { if km.CoordinateSystem == cs { return km } kc, err := repo.getKilometerConvert(km.CoordinateSystem, cs) if err != nil { panic(err) } var sourceCsKm *proto.Kilometer var targetCsKm *proto.Kilometer if kc.KmA.CoordinateSystem == km.CoordinateSystem { sourceCsKm = kc.KmA targetCsKm = kc.KmB } else { sourceCsKm = kc.KmB targetCsKm = kc.KmA } value := targetCsKm.Value + (km.Value - sourceCsKm.Value) if value < 0 { panic(fmt.Sprintf("公里标[%v]转换为坐标系[%s]的公里标的值[%d]小于0", km, cs, value)) } return &proto.Kilometer{Value: value, CoordinateSystem: cs} } func (repo *Repository) addKilometerConvert(kc *proto.KilometerConvert) { repo.kilometerConvertMap[buildKilometerConvertKey(kc.KmA.CoordinateSystem, kc.KmB.CoordinateSystem)] = kc repo.kilometerConvertMap[buildKilometerConvertKey(kc.KmB.CoordinateSystem, kc.KmA.CoordinateSystem)] = kc } func (repo *Repository) getKilometerConvert(cs1, cs2 string) (*proto.KilometerConvert, error) { convert := repo.kilometerConvertMap[buildKilometerConvertKey(cs1, cs2)] if convert == nil { return nil, errors.New(fmt.Sprintf("没有[%s-%s]的公里标转换数据", cs1, cs2)) } return convert, nil } func buildKilometerConvertKey(cs1 string, cs2 string) string { return cs1 + cs2 }