证券化率,也就是两市的总市值/GDP,如果是70%-80%(在美国市场)是比较好的买入时机,如果达到200%买入,是玩火。
数据来源:上海证券交易所和深圳证券交易所官方网站上有公布总市值。
GDP 6%增长是底线。
加息虽然是利空,但是往往是买入时机,因为加息往往是在经济好的时候,而且往往实际利率还是负,政府为了防止经济过热。第一轮加息往往是买入时机。
人民币升值对出口企业的不利影响,专家说人民币升值每年不炒过5%是能够承受的。
证券化率,也就是两市的总市值/GDP,如果是70%-80%(在美国市场)是比较好的买入时机,如果达到200%买入,是玩火。
数据来源:上海证券交易所和深圳证券交易所官方网站上有公布总市值。
公允的表达资产减损的情况,是近年来财务报表编制最重要的发展方向之一。但是,对公司而言,根本之计还是管理资产减损,避免资产质量恶化。以下列出两项重点加以说明:控制存货跌价风险、控制应收账款倒账风险。
另外通过签订存货跌价保护契约的方式,通路商可让制造商补贴产品价格下跌的部分或全部损失。通路商除了先签订这种契约外,也需要求经理人能系统的执行这些条款,这就涉及到经理人的执行力。
针对本身拥有的存货,要加快出售现有存货的速度(存货周转率),是通路商管理的重点。直截了当的做法是把存货周转速度列入卖场经理人的绩效评估指标。
至于制造商,它们主要以先下单后生产、增加存货周转速度来降低存货风险。
20世纪80年代,丰田汽车创造了零库存的管理模式 有市场需求才制造汽车,在制造时才将零部件送上生产线。这种创新的管理流程,大幅降低了汽车成本、半成品及零部件存货的风险。
鸿海(富士康为其相关企业)生产线执行严格的材料库存控制,创造了生产成本的竞争力。鸿海工厂的备料时间比同业短,当备料到一定时间还没出货,就会被打成库存呆料,先折价一半。经理人如果没有严格执行生产计划时间表、准确的拿捏出货时间,财务报表上的业绩就会变差,甚至会拿不到年终奖金,这种机制使得经理人严格控制材料库存。
除了落实客户信用调查外,为避免应收账款发生倒账风险,部分企业会将应收账款卖断给金融机构。这种交易会让公司资产负债表的营收账款金额减少、现金金额增加。但是,有些银行为求自保,要求现金必须存放在该银行,万一有倒账情况发生,银行可优先由该公司存款余额中直接扣款。如此一来,现金并非完全由公司自有支配,反而成为受限制资产。就财务报表公允揭露的精神而言,现金中受到限制的部分,应该在附注中加以解释。就务实的管理来说,应收账款卖断能否达到风险转移的目的,经理人应在相关契约上加以理清。
此外还有一个使应收账款倒账风险增加的原因:不恰当的绩效评估制度。如果销售人员的奖金完全根据业绩而定,可能会诱使销售人员忽略客户是否有还款意愿与能力。信用风险的控制,不该完全推给后段的财务和稽核人员。
命令模式就是将请求封装为一个对象,从而使你可用不同的请求对客户进行参数化; 对请求排队或记录请求日志,以及支持可撤销的操作。
在软件系统中,行为请求者与行为实现者通常是一种紧耦合的关系,但某些场合,比如需要对行为进行记录、撤销或重做、事务等处理时,这种无法抵御变化的紧耦合的设计就不太合适。
这是一个遥控器的例子
一个灯类,有开灯、关灯、昏暗灯光之类的方法。
一个接口命令类:定义了执行和撤销两个方法。
下面有四个类实现了命令接口,分别是:开灯命令、关灯命令、昏暗开灯命令、昏暗关灯命令。
一个遥控器类,在模式中叫做调度者,依赖命令接口,调用命令的方法。
客户类,上图没有画,初始化命令类,传入遥控器类,调用遥控器类相应方法。
代码:
Light.java:
package headfirst.command.undo; public class Light { String location; int level; public Light(String location) { this.location = location; } public void on() { level = 100; System.out.println("Light is on"); } public void off() { level = 0; System.out.println("Light is off"); } public void dim(int level) { this.level = level; if (level == 0) { off(); } else { System.out.println("Light is dimmed to " + level + "%"); } } public int getLevel() { return level; } }
命令接口 Command.java:
package headfirst.command.undo; public interface Command { public void execute(); public void undo(); }
开灯命令 LightOnCommand.java:
package headfirst.command.undo; public class LightOnCommand implements Command { Light light; public LightOnCommand(Light light) { this.light = light; } public void execute() { light.on(); } public void undo() { light.off(); } }
关灯命令 LightOffCommand.java:
package headfirst.command.undo; public class LightOffCommand implements Command { Light light; public LightOffCommand(Light light) { this.light = light; } public void execute() { light.off(); } public void undo() { light.on(); } }
昏暗开灯命令 DimmerLightOnCommand.java:
package headfirst.command.undo; public class DimmerLightOnCommand implements Command { Light light; int prevLevel; public DimmerLightOnCommand(Light light) { this.light = light; } public void execute() { prevLevel = light.getLevel(); light.dim(75); } public void undo() { light.dim(prevLevel); } }
昏暗关灯 DimmerLightOffCommand.java:
package headfirst.command.undo; public class DimmerLightOffCommand implements Command { Light light; int prevLevel; public DimmerLightOffCommand(Light light) { this.light = light; prevLevel = 100; } public void execute() { prevLevel = light.getLevel(); light.off(); } public void undo() { light.dim(prevLevel); } }
空命令 NoCommand.java:
package headfirst.command.undo; public class NoCommand implements Command { public void execute() { } public void undo() { } }
遥控器 RemoteControlWithUndo.java:
package headfirst.command.undo; import java.util.*; // // This is the invoker // public class RemoteControlWithUndo { Command[] onCommands; Command[] offCommands; Command undoCommand; public RemoteControlWithUndo() { onCommands = new Command[7]; offCommands = new Command[7]; Command noCommand = new NoCommand(); for(int i=0;i<7;i++) { onCommands[i] = noCommand; offCommands[i] = noCommand; } undoCommand = noCommand; } public void setCommand(int slot, Command onCommand, Command offCommand) { onCommands[slot] = onCommand; offCommands[slot] = offCommand; } public void onButtonWasPushed(int slot) { onCommands[slot].execute(); undoCommand = onCommands[slot]; } public void offButtonWasPushed(int slot) { offCommands[slot].execute(); undoCommand = offCommands[slot]; } public void undoButtonWasPushed() { undoCommand.undo(); } public String toString() { StringBuffer stringBuff = new StringBuffer(); stringBuff.append("\n------ Remote Control -------\n"); for (int i = 0; i < onCommands.length; i++) { stringBuff.append("[slot " + i + "] " + onCommands[i].getClass().getName() + " " + offCommands[i].getClass().getName() + "\n"); } stringBuff.append("[undo] " + undoCommand.getClass().getName() + "\n"); return stringBuff.toString(); } }
入口类:
package headfirst.command.undo; public class RemoteLoader { public static void main(String[] args) { RemoteControlWithUndo remoteControl = new RemoteControlWithUndo(); Light livingRoomLight = new Light("Living Room"); LightOnCommand livingRoomLightOn = new LightOnCommand(livingRoomLight); LightOffCommand livingRoomLightOff = new LightOffCommand(livingRoomLight); remoteControl.setCommand(0, livingRoomLightOn, livingRoomLightOff); remoteControl.onButtonWasPushed(0); remoteControl.offButtonWasPushed(0); System.out.println(remoteControl); remoteControl.undoButtonWasPushed(); remoteControl.offButtonWasPushed(0); remoteControl.onButtonWasPushed(0); System.out.println(remoteControl); remoteControl.undoButtonWasPushed(); CeilingFan ceilingFan = new CeilingFan("Living Room"); CeilingFanMediumCommand ceilingFanMedium = new CeilingFanMediumCommand(ceilingFan); CeilingFanHighCommand ceilingFanHigh = new CeilingFanHighCommand(ceilingFan); CeilingFanOffCommand ceilingFanOff = new CeilingFanOffCommand(ceilingFan); remoteControl.setCommand(0, ceilingFanMedium, ceilingFanOff); remoteControl.setCommand(1, ceilingFanHigh, ceilingFanOff); remoteControl.onButtonWasPushed(0); remoteControl.offButtonWasPushed(0); System.out.println(remoteControl); remoteControl.undoButtonWasPushed(); remoteControl.onButtonWasPushed(1); System.out.println(remoteControl); remoteControl.undoButtonWasPushed(); } }
目标:一个主题类,当主题类发生某种变化的时候,会调用观察者类的一个方法。来达到类似监听的效果,比如图形界面设计中,一个按钮按下去的响应其实就是使用观察者模式实现的。
UML图不太会用,暂时用语言补充一下,首先这是一个有关气象的示例代码,一个气象数据类(在观察者模式中是subject),几个公告板(在观察者模式中作为观察者)。要实现的时候当气象数据类发生变化的时候,会调用在气象数据类中注册了的观察者的 update方法,然后观察者(也就是布告板)会经过处理然后显示出来。
气象数据类实现接口subject 接口,公告板类实现 Observer和 DisplayElement接口。其中 DisplayElement接口定义了 display方法,用来显示内容。Observer接口定义了update方法,供气象数据类(subject的实现)调用。
接口 subject定义了三个方法:
public void registerObserver(Observer o); public void removeObserver(Observer o); public void notifyObservers();
分别是用来注册、移除和通知观察者。其中 notifyObservers()调用的是观察者的 update()。注册和移除的调用方法是:在new 观察者的时候把subject作为参数传递给观察者的构造函数,然后在构造函数中就可以调用subject的registerObserver了,而且这样并不需要担心性能,因为php对象的传递其实传递的是引用。
下面粘贴具体的代码:
Subject 接口(定义了注册、移除、通知观察者的方法):
package headfirst.observer.weather; public interface Subject { public void registerObserver(Observer o); public void removeObserver(Observer o); public void notifyObservers(); }
Observer 接口(定义了观察者的update方法):
package headfirst.observer.weather; public interface Observer { public void update(float temp, float humidity, float pressure); }
DisplayElement 接口(定义了显示方法):
package headfirst.observer.weather; public interface DisplayElement { public void display(); }
WeatherData类,subject接口的实现:
package headfirst.observer.weather; import java.util.*; public class WeatherData implements Subject { private ArrayList observers; private float temperature; private float humidity; private float pressure; public WeatherData() { observers = new ArrayList(); } public void registerObserver(Observer o) { observers.add(o); } public void removeObserver(Observer o) { int i = observers.indexOf(o); if (i >= 0) { observers.remove(i); } } public void notifyObservers() { for (int i = 0; i < observers.size(); i++) { Observer observer = (Observer)observers.get(i); observer.update(temperature, humidity, pressure); } } public void measurementsChanged() { notifyObservers(); } public void setMeasurements(float temperature, float humidity, float pressure) { this.temperature = temperature; this.humidity = humidity; this.pressure = pressure; measurementsChanged(); } // other WeatherData methods here public float getTemperature() { return temperature; } public float getHumidity() { return humidity; } public float getPressure() { return pressure; } }
下面是几个公告板(也就是观察者):
CurrentConditionsDisplay 类:
package headfirst.observer.weather; public class CurrentConditionsDisplay implements Observer, DisplayElement { private float temperature; private float humidity; private Subject weatherData; public CurrentConditionsDisplay(Subject weatherData) { this.weatherData = weatherData; weatherData.registerObserver(this); } public void update(float temperature, float humidity, float pressure) { this.temperature = temperature; this.humidity = humidity; display(); } public void display() { System.out.println("Current conditions: " + temperature + "F degrees and " + humidity + "% humidity"); } }
StatisticsDisplay 类:
package headfirst.observer.weather; import java.util.*; public class StatisticsDisplay implements Observer, DisplayElement { private float maxTemp = 0.0f; private float minTemp = 200; private float tempSum= 0.0f; private int numReadings; private WeatherData weatherData; public StatisticsDisplay(WeatherData weatherData) { this.weatherData = weatherData; weatherData.registerObserver(this); } public void update(float temp, float humidity, float pressure) { tempSum += temp; numReadings++; if (temp > maxTemp) { maxTemp = temp; } if (temp < minTemp) { minTemp = temp; } display(); } public void display() { System.out.println("Avg/Max/Min temperature = " + (tempSum / numReadings) + "/" + maxTemp + "/" + minTemp); } }
还有几个观察者,篇幅原因不在粘贴了 .....
下面是两个入口类:
WeatherStation类:
package headfirst.observer.weather; import java.util.*; public class WeatherStation { public static void main(String[] args) { WeatherData weatherData = new WeatherData(); CurrentConditionsDisplay currentDisplay = new CurrentConditionsDisplay(weatherData); StatisticsDisplay statisticsDisplay = new StatisticsDisplay(weatherData); ForecastDisplay forecastDisplay = new ForecastDisplay(weatherData); weatherData.setMeasurements(80, 65, 30.4f); weatherData.setMeasurements(82, 70, 29.2f); weatherData.setMeasurements(78, 90, 29.2f); } }
WeatherStationHeatIndex类:
package headfirst.observer.weather; import java.util.*; public class WeatherStationHeatIndex { public static void main(String[] args) { WeatherData weatherData = new WeatherData(); CurrentConditionsDisplay currentDisplay = new CurrentConditionsDisplay(weatherData); StatisticsDisplay statisticsDisplay = new StatisticsDisplay(weatherData); ForecastDisplay forecastDisplay = new ForecastDisplay(weatherData); HeatIndexDisplay heatIndexDisplay = new HeatIndexDisplay(weatherData); weatherData.setMeasurements(80, 65, 30.4f); weatherData.setMeasurements(82, 70, 29.2f); weatherData.setMeasurements(78, 90, 29.2f); } }
可以看到观察者的创建过程,大家可以编译执行一下,看看显示的结果是否如预期。
话说池塘有一群鸭子,其中有各种颜色的,有玩具鸭子,有木头鸭子,有真正的鸭子,鸭子有各种颜色的,红头鸭、绿头鸭等等,有的行为是飞、叫。如果用策略模式如何定义呢?
把飞行的行为和呱呱叫的行为分别定义接口,其实就是封装了起来。对于Duck类的子类,可以动态的加载行为类,然后调用相应的方法。不管是加载呱呱叫还是吱吱叫,调用的接口相同,这有点向上转型的意思。
代码:
Duck.java 鸭子的超类
public abstract class Duck { FlyBehavior flyBehavior; QuackBehavior quackBehavior; public Duck() { } public void setFlyBehavior(FlyBehavior fb) { flyBehavior = fb; } public void setQuackBehavior(QuackBehavior qb) { quackBehavior = qb; } public abstract void display(); public void performFly() { flyBehavior.fly(); } public void performQuack() { quackBehavior.quack(); } public void swim() { System.out.println("All ducks float, even decoys!"); } }
MallardDuck.java 野鸭
public class MallardDuck extends Duck { public MallardDuck() { quackBehavior = new Quack(); flyBehavior = new FlyWithWings(); } public void display() { System.out.println("I'm a real Mallard duck"); } }
ModelDuck.java 模型鸭
public class ModelDuck extends Duck { public ModelDuck() { flyBehavior = new FlyNoWay(); quackBehavior = new Quack(); } public void display() { System.out.println("I'm a model duck"); } }
FlyBehavior.java 飞行行为类的接口
public interface FlyBehavior { public void fly(); }
FlyNoWay.java 飞行接口的实现 不能飞
public class FlyNoWay implements FlyBehavior { public void fly() { System.out.println("I can't fly"); } }
FlyRocketPowered.java 飞行接口的实现 火箭飞行
public class FlyRocketPowered implements FlyBehavior { public void fly() { System.out.println("I'm flying with a rocket!"); } }
FlyWithWings.java 飞行接口的实现 飞行
public class FlyWithWings implements FlyBehavior { public void fly() { System.out.println("I'm flying!"); } }
QuackBehavior.java 呱呱叫行为接口
public interface QuackBehavior { public void quack(); }
Quack.java 呱呱叫接口的实现
public class Quack implements QuackBehavior { public void quack() { System.out.println("Quack"); } }
Squeak.java 呱呱叫接口的实现 吱吱叫
public class Squeak implements QuackBehavior { public void quack() { System.out.println("Squeak"); } }
MuteQuack.java 呱呱叫接口的实现 沉默
public class MuteQuack implements QuackBehavior { public void quack() { System.out.println("<< Silence >>"); } }
MiniDuckSimulator.java 入口类
public class MiniDuckSimulator { public static void main(String[] args) { Duck mallard = new MallardDuck(); mallard.performQuack(); mallard.performFly(); Duck model = new ModelDuck(); model.performFly(); model.setFlyBehavior(new FlyRocketPowered()); model.performFly(); } }
不过多解释了,有时候看代码比看图、看注释还一目了然,正所谓好的代码是自解释的。