USCPA AUD試験受験体験記(2019年1月)※長文です

AUD概論

2019年1月受験(BECと同日受験)で、AUDには85点で1発合格していた。自分の回ではテストレット1が圧倒的に難しく、テストレット2は明らかに簡単(ちなみにBECでも同じことを書いた)。テストレット2が難しくないと受からないというのがUSCPAの通説なので、これはもうだめかと思ったが、蓋を開けてみればまずまずの点数で合格していた。近年のUSCPA試験ではテストレット間の難易度変化は気にしなくて良いのかもしれない。Simulation問題も文章量がとにかく多いので、気持ちが折れそうになったが、最後の1秒まで粘って解き切ることが絶対重要。

f:id:tranche:20190208064227p:plain

私には特に監査に関する経験や知識は無く、ずぶの素人として学習を開始。日本でもアメリカでも、監査論を教えてもらえる大学や学部は、ごく一部に限られるのではないかと思っている。ちなみに私が学士で通った筑波大学では、会計に関する授業は当時で1~2個しか無く、監査論の授業を取るチャンスも無かったのである(当時からCPAには興味があって、かなり調べていた)。就職してからは、IT部門として、PwCあらた監査法人の先生に言われたとおりに資料を渡したりとかしたことは多少あったが、そもそも何の手続きとしてそういうことをしているのかなどの理解は全く持ち合わせていなかった。

勉強方法としては、まずプロアクティブの講義を一通り聞いた。プロアクティブの佐々木先生は、話が面白い。その中でもAUDは一番面白い部類に入るのではないだろうか?内部統制を蕎麦屋のおばちゃんに例えて説明してくれるのが、笑えたし、理解を深める助けになったのではないかと思う。一通り佐々木先生の講義を聞いて笑った後は、プロアクティブのテキストの要点をさらにまとめた、自分専用のまとめノートを作ることにした。このまとめノートは、なかなか作るのに骨が折れたが、AUDに関しては作ってよかったと思っている。時間をかけて作ることで愛着もわいてきて、何度も読み返して知識の定着に役立った。プロアクティブのテキストで足りないものとか、問題演習で間違えたものの解説などは、ノートの後ろにどんどん追加していくことで、最終的にかなりの大作に育った。AUDを勉強した期間としては、全部で5ヶ月といったところか(途中出願手続きに時間がかかったこともあって、何もしない中だるみ時期もあった)。問題演習では、GleimのMega Test Bankを使った。Gleimを選んだ理由は、安くてボリュームがあったのと、むずかしめに作られているという評判を聞いたからである。プロアクティブでも演習問題はたくさん用意してくれているが、UI(ユーザーインターフェイス)が気に入らなかったので使わなかった。GleimやBeckerなら、基本的に本試験と同じUIで問題演習できるので、お金に多少余裕がある人であればそっちを使うことをおすすめする。以下、長文となり申し訳ないが、私なりのAUD試験攻略のツボを記しておく。

f:id:tranche:20190208021328j:plainf:id:tranche:20190208030352j:plainf:id:tranche:20190208021242j:plain
自作ノートの例(ご参考)

監査と内部統制

AUDを勉強するまでは、会計監査というのは、1つの誤謬も漏らさずキャッチする性質のものだと理解していた。しかしAUDを勉強してみて、そうではないということがまず分かった。現実的に考えてみれば確かに当然の話しで、1個1個のアカウントまで軽重つけずに精査していたのでは、ただでさえ会計士が人手不足の中、時間がいくらあっても足りないし期日に間に合わないだろう。だが世の中には時に、会社ぐるみで粉飾や違法行為に手を染め、積極的に騙しにかかってくるような本当にやばい会社というのも存在する。だから、その会社がやばいことをしていそうかどうか、それによって監査の軽重や力点は変わってくる。その見極めに使われるのが、内部統制である。つまり、内部統制がしっかり設計されていて、会計士の目から見ても正しく運用されているのならば、その会社のやっていることを大体信じても大丈夫だね(だから血眼で精査しなくても良いね)と考える。だから会計士は、その会社の内部統制の出来を見て、監査リスクが一定になるように監査の方向性を決定する(AR=IR×CR×DRの式)。監査と内部統制は切っても切れない関係にあるし、だから内部統制はどこの会社でも重要性が叫ばれているのである(それが本当に良いことなのかどうかは分からないが、現代の監査論ではそういう立て付けになっている)。この考え方が、AUD試験の根幹となる。

監査の種類・手続き

AUD試験といっても、取扱うのは、実は監査(Audit)だけではない。Audit/Review/Compilation/Preparation/Attestationなどの色々な種類が出題されて、沿うべき基準と手続きが少しずつ異なってくる。また、上場しているかしていないかでも、基準や手続きがが異なってくる。なので理想を言うと、監査の種類によって異なる手続きを俯瞰できるような、一覧表があったほうが本当は良いと思う(私には結局作れなかったが・・・)。頻出論点の例を挙げると、SSARSに従う非上場企業のReview手続きでは、内部統制の理解は求められない。しかしこれが上場企業となるとSOX法・PCAOB基準となり監査と内部統制監査がマストになってくる。PCAOBかGAASかで、レポートの文言もかなり違ってくるので、差をしっかり意識する必要あり。私が受けた実際の試験のリサーチ問題で、同じ論点ではあるがPCAOBかAICPAかが分かれるような引っ掛け問題が出たので、上場・非上場の違いはとても重要。

監査の流れと意見

監査手続きを定めた基準がGAASで、会計基準GAAPであり、監査というのは基本的にその両輪で見ていくことになる(場合によって、異なる基準を使うことはありえるが、監査手続・会計基準の両輪で見るというのは一緒)。だから不備が発見された場合には、どの部分で不備があるのかで出す意見は変わってくる。例えば、十分な監査手続ステップを踏めなかったということであれば、それはGAASに関する不備だから最悪Disclaimerになるが、数字が間違っているのにマネジメントが修正してくれない場合は、GAAPの問題としてAdverse意見ということになる。どういうケースで何の意見を出すのか、このパターンをしっかりと理解していることがAUD試験では重要になってくるものと思われる(事象の軽重によってQualifiedかDisclaimerなのかボヤッとしていることもあるので、なかなかこれが難しい)。

f:id:tranche:20190208192224j:plain
自作のフローチャート(ご参考)

USCPA BEC試験受験体験記(2019年1月)※長文です

BEC概論

2019年1月受験(AUDと同日受験)で、BECには86点で1発合格していた。自分の回ではテストレット1が圧倒的に難しく、テストレット2は明らかに簡単(1では計算も多くて3問くらい適当にクリックする羽目になったが、2では単語定義を問うような問題ばかり)。テストレット2が難しくないと受からないというのがUSCPAの通説なので、これはもうだめかと思ったが、蓋を開けてみればまずまずの点数で合格していた。AUDでも似たような感覚があったので、近年のUSCPA試験ではテストレット間の難易度変化は気にしなくて良いのかもしれない。Simulation問題も文章量がとにかく多いので、気持ちが折れそうになったが、最後の1秒まで粘って解き切ることが絶対重要。

f:id:tranche:20190208064227p:plain


私にはMBAかつITのバックグラウンドがあったこともあり、BECについては何とかなるだろうとタカをくくって後回しにしていた。ところが試験1ヶ月前ごろから準備をしはじめて感じたこと―もちろんバックグラウンドが助けになったことは間違いないが、かといってBECが楽勝だったかといえば決してそうではなかったというのが実感である。というのも、BECで問われる知識は広く浅くが基本なので、知らない用語もたくさん出てくる上に、試験では独特の形式・定義で問われることがあるからである。独特の問われ方というのはつまり、紛らわしいチョイスであるとか、自分の感覚とは微妙にズレた用語定義、丸暗記していないと解けないような問題とかが出てくる。MBAであるとかITの実務経験というのは、思考力を要する問題には役に立つが、BECで問われる問題ではそれほどの思考力が要らない代わり、基礎事項を正確に記憶すること(そしてBEC試験の意に沿う通りの定義で覚えること)が重要になってくるのではないかと考える。

勉強方法としては、Gleimの紙テキストブック(GleimのMega Test Bankを買ったらなぜか無料で送られてきたもの)を使うことにした。プロアクティブの講義も1周聞いてみたが、Gleimにしか載っていない事項が多く、広く浅くのBEC試験ではGleimの方が良いと思ったからである。一通りの事項が載っているなら、GleimでもBeckerでもテキストは何でも良いと思う。繰り返しになるが広く浅くの試験なので、カバーされている事項は多いほうが良いが深入りはせず、重要単語をマーカーしたりその横にボールペンでノートを書くにとどめた。BECについては自分用のまとめノートは作らなかった。その理由としては、あまりに広範囲で散逸的な試験のため費用対効果が薄いと思ったこと、将来的に読み返すこともきっと無いだろうと思ったためである。以下、長文で申し訳ないが感じたことを各論で記す。

f:id:tranche:20190208192807p:plain
Gleimなら問題演習は本番そっくり

内部統制

BECでは、内部統制(特にCOSOフレームワーク)が頻繁に問われる。ビジネスと言うよりもはやCOSOの試験ではないかと思うほど、COSOの事項はBECの合格に欠かせないものと考えられる。私はAUDを先行して学習していたが、私の感覚ではBECとAUDでオーバーラップする知識はあまり無かった(もちろん、AUDを勉強したことでBECの内部統制を理解する助けになったことには間違いない)。というのも、AUDではCOSOフレームワーク(立方体で図示されることが多い)単体はそこまで深掘りせず、監査の種類とか手続きに力点を置くからである。だから、AUDをやっていればBECの内部統制が大丈夫かといえば決してそうではない、BECにはBEC用の勉強が必要だったというのが率直な感想。

経済学

BECで問われる経済学の知識は、驚くほど浅い印象を受けた。私は日本の証券アナリスト(CMA)も持っているが、その経済学パートを更に5分の1に薄めたような感じがした。配点も低いので捨ててしまっても良いとは思うが、ミクロでは需供曲線と弾力性、マクロではGDP計算の数式とか乗数効果くらいがわかっていればBECでは大丈夫だと思う(ビジネスマンとしてそんなことで良いのかという気持ちはあるが、BECのレベルはそれが実情)。

ファイナンス

ファイナンス理論は、CAPMとか債券の基礎事項、配当割引モデル、レシオ、NPV等が出る。日本の証券アナリスト(CMA)の証券分析パートを3分の1に薄めたような印象。基礎的な事項がわかっていれば大丈夫だと思うが、経済学と違ってファイナンスは捨てるわけにはいかない印象。割引率の考え方が全ての根底にあるので、ファイナンス初学者の場合はそこをまず押さえれば、あとは丸暗記でも良いと思う。

IT

ITの出題量は、COSOに並んでBEC試験の多くを占める印象。ITは内部統制と切っても切れないという考え方が、それだけCPAの試験でITが多く問われる理由だと思う。したがって、ITといっても公認会計士としての目線・内部統制目線で答えてあげることが重要になってくる。ITのバックグラウンドがある人であっても(むしろITのバックグランドがあるからこそ?)、BECのITで苦戦しかねない理由がここにある。自分の理解とは微妙にズレた形で用語が定義されていたり、情報工学の学位を持っていても聞いたことが無いコンセプトが出てくることに注意。一例で言うと、第1世代~第5世代でプログラミング言語を分類するとかいう考え方がそれにあたる。私が無知なだけかもしれないが、そういう考え方はBECをやるまで知らなかった。そのモデルだと、CとかJavaは全部一緒くたに第3世代に入るらしいが、ITの人間は普通そういう考え方はしないものなのである(Cの方が低レイヤー、あるいはオブジェクト指向か否かで普通分けるし、世代というより適材適所で使うべきものとして考える)。だがBEC試験に合格したいのであれば、BECが決めた形で覚えて回答してあげないといけない。悲しいことだが、BEC試験では公認会計士としての共通知識を問うているのであって、あなたの考え方は問うてないのである。このギャップに私はかなり苦しめられた。

その他ビジネス事項

材料の発注とか、資金繰り、支払いサイト(例えばネット30)のような知識が問われる。MBAの授業で習ったこともあるが、実務経験も無いし、もう忘却の彼方にあったような知識。早期支払割引のコストなど、初めて知るような内容も多かった。なぜそういう数式になるのか理解できないこともあったが、下手に詰まらずに、そういうものなのだと暗記で乗り切ることにした。

管理会計

個人的には苦手な分野だったが、比較的よく問われるので捨てるわけにはいかない。配賦基準とか固定費と変動費だとか、MBAとか簿記2級でやったことがあるのは間違いないが、とにかく苦手意識の高い分野だった。管理会計について苦手な私から言えることは少ないが、MCQよりはSimulation問題で多く問われるので、思考できるレベルまで学習しておかないと芋づる式に落としてしまう可能性もある怖い分野。

Written Communication

日本人であれば誰しもが気にするWC問題。私は特にWC専用の対策はしなかったが、BECの勉強を通じてWCでも使えるような知識を身につけることを意識した。WCというのは基本的にプロコン(Pros/Cons、メリット・デメリット)を問うてくるので、知識をインプットする際にはその方式のメリット・デメリットも考えながら覚えるようにした。実際の試験では、現金しか受け取らない商売をしているが売掛金も受け付けるようにしてはどうかとか、取締役として選ばれることによる責任は何かみたいなことが問われた(もう1問あったが、難しすぎてほぼ白紙の時間切れになったので、出題内容も覚えていない)。英語のライティング力がそこそこある前提ではあるが、そこまで恐れる必要な無いのではないかという印象(英語力が足りない場合は、メリット・デメリットが分かっていてもそれをうまく表現できない可能性あり。その場合は、トピックごとにヤマをかけて文を丸暗記するとかそういう荒療治で乗り切ることも必要になってくるかもしれない)。

米国株の執行方法を忘れやすいので日本語で整理

A market order is an order to buy or sell a security immediately. This type of order guarantees that the order will be executed, but does not guarantee the execution price. A market order generally will execute at or near the current bid (for a sell order) or ask (for a buy order) price. However, it is important for investors to remember that the last-traded price is not necessarily the price at which a market order will be executed.
成行: Market Orderは売買を直ちに行う発注方法です。この場合、必ず執行はしますが、執行価格が何になるかは分かりません。

A limit order is an order to buy or sell a security at a specific price or better. A buy limit order can only be executed at the limit price or lower, and a sell limit order can only be executed at the limit price or higher. Example: An investor wants to purchase shares of ABC stock for no more than $10. The investor could submit a limit order for this amount and this order will only execute if the price of ABC stock is $10 or lower.
指値: Limit Orderとは、特定の執行価格またはそれよりも良い執行価格で約定させる発注方法です。例えば買いの場合、Limit Priceかそれより低い価格で約定が行われます。

A stop order, also referred to as a stop-loss order is an order to buy or sell a stock once the price of the stock reaches the specified price, known as the stop price. When the stop price is reached, a stop order becomes a market order.
指値: ストップロスとも呼ぶ。指値注文が現在よりも有利なレートを指定するのに対し、逆指値は、現在のレートよりも不利なレートを指定して発注する注文方法です。市場価格に抵触した瞬間にMarket Order(成行)で発注が行われます。
A buy stop order is entered at a stop price above the current market price. Investors generally use a buy stop order to limit a loss or protect a profit on a stock that they have sold short. A sell stop order is entered at a stop price below the current market price. Investors generally use a sell stop order to limit a loss or protect a profit on a stock they own.
投資家は一般的に、リスクを限定する目的で逆指値を置きます。

www.investor.gov

今面白い変わり種の米国REITを10銘柄

(1) American Tower Corporation (AMT)
時価総額:$60.3十億ドル
配当利回り:2.0%
・主に電波塔の運営を16カ国で行う
・USにおいてはVerizon, AT&Tの5Gサービス展開をサポートする戦略
・配当性向40%を保ちつつ、今年は前年比120%の配当を予想

(2) CorEnergy Infrastructure Trust (CORR)
時価総額:$458.6百万ドル
配当利回り:7.7%
・パイプライン等のエネルギー関連インフラに投資
天然ガスパイプライン、液化ガス保管システム、海洋原油パイプラインなどを全米に保有
・エネルギー事業に必須かつ参入障壁が高い設備に重点的に投資

(3) CoreSite Realty (COR)
時価総額:$3.6十億ドル
配当利回り:3.6%
・全米にデータセンターを20物件保有。1,200以上の顧客基盤
・23%の堅調なFFO成長率

(4) Crown Castle International (CCI)
時価総額:$41.9十億ドル
配当利回り:4.0%
・全米に携帯電話向け電波塔を運営
・14%のFFO成長率、アナリストレーティングも押しなべて強気

(5) Digital Realty Trust (DLR)
時価総額:$21.5十億ドル
配当利回り:3.5%
・世界で205物件のデータセンターを運営
・設備更改のための資産売却は過去3年で3億ドルにのぼる
・13年連続増配

(6) Gladstone Land (LAND)
時価総額:$177.8百万ドル
配当利回り:4.2%
・全米に農地を所有。特にフルーツや野菜用地に注力しており、これらは価格変化がコモディティ(コーン等)に比べて穏やかと言われる
・賃料は年約9%の上昇中、収益は2013年から6倍へ

(7) Hannon Armstrong Sustainable Infrastracture (HASI)
時価総額:$1.0十億
配当利回り:6.7%
ソーラーパネル、風車などの再生可能エネルギーに投資
・特に風車の利用量が収益成長のカギとなる。またソーラーパネルもコスト競争力がつき始めている
・配当は年26%のペースで増加中

(8) Iron Mountain (IRM)
時価総額:$9.7十億ドル
配当利回り:6.7%
・世界で1,400物件のデータセンターを運営。Fortune 1000企業の95%が顧客
・2018年中はM&Aにより新興国へも進出の見込み

(9) Lamar Advertising Company (LAMR)
時価総額:$6.6十億ドル
配当利回り:5.3%
ビルボードや空港ターミナル内の広告などを保有する、全米最大規模の屋外広告企業
・北米で15万物件近いビルボード保有
プエルトリコのハリケーンの影響で収益鈍化も、中間選挙を前にした選挙広告等で巻き返す見込み

(10) Weyerhaeuser(WY)
時価総額:$27.6十億ドル
配当利回り:3.5%
・北米で森林用地を保有する最大規模の事業者
ウルグアイからは撤退し、ポートフォリオの簡素化

このページは以下の記事の和訳概要版です
www.kiplinger.com

メモ帳で職場のスクリーンセーバーを無効化する

職場のパソコンというものは、通常何らかのセキュリティが講じられています。例えば小職が前にいた会社では、5分おきに強制的にスクリーンセーバーがかかってしまい、ちょっと目を離した隙にPCがロックされる面倒が発生していました。理由があってのセキュリティではあるのは間違いないですが、それも度が過ぎると非効率の根源です。開発環境を自由に入れられない職場ですが、C#コンパイラWindows標準でついてくることが分かりましたので、暇つぶしにスクリーンセーバーを起動させないexeを調べながら作ってみました。

コンパイルのやりかた
C:\Windows\Microsoft.NET\Framework\v2.0.50727\csc.exe /target:winexe C:\temp\ScreenSaverKiller.cs


ScreenSaverKiller.cs

using System;
using System.Drawing;
using System.Collections;
using System.ComponentModel;
using System.Windows.Forms;
using System.Data;
using System.Text;
using System.Diagnostics;
using System.Runtime.InteropServices;

namespace WindowsApplication1
{
    public class Form1 : System.Windows.Forms.Form
    {
        private System.Windows.Forms.Label label1;
        private System.Windows.Forms.Timer timer1;
        private System.Windows.Forms.Button button1;
        private System.ComponentModel.IContainer components;

        public Form1()
        {
            InitializeComponent();
        }
        protected override void Dispose(bool disposing)
        {
            if (disposing)
            {
                if (components != null)
                {
                    components.Dispose();
                }
            }
            base.Dispose(disposing);
        }


        #region Windows Form Designer
        private void InitializeComponent()
        {
            this.components = new System.ComponentModel.Container();
            this.label1 = new System.Windows.Forms.Label();
            this.timer1 = new System.Windows.Forms.Timer(this.components);
            this.button1 = new System.Windows.Forms.Button();
            this.SuspendLayout();

            this.label1.Font = new System.Drawing.Font("MS UI Gothic", 36F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((System.Byte)(128)));
            this.label1.Location = new System.Drawing.Point(16, 16);
            this.label1.Name = "label1";
            this.label1.Size = new System.Drawing.Size(384, 64);
            this.label1.TabIndex = 0;
            this.label1.Text = "label1";
            this.label1.TextAlign = System.Drawing.ContentAlignment.MiddleCenter;

            this.timer1.Enabled = true;
            this.timer1.Interval = 10;
            this.timer1.Tick += new System.EventHandler(this.timer1_Tick);

            this.button1.Location = new System.Drawing.Point(109, 96);
            this.button1.Name = "button1";
            this.button1.Size = new System.Drawing.Size(192, 32);
            this.button1.TabIndex = 1;
            this.button1.Text = "Move cursor to the center";
            this.button1.Click += new System.EventHandler(this.button1_Click);

            this.AutoScaleBaseSize = new System.Drawing.Size(5, 12);
            this.ClientSize = new System.Drawing.Size(410, 144);
            this.Controls.Add(this.button1);
            this.Controls.Add(this.label1);
            this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
            this.Name = "Form1";
            this.Text = "ScreenSaverKiller";
            this.ResumeLayout(false);
        }
        #endregion

        [STAThread]
        static void Main()
        {
            Application.Run(new Form1());
        }

        private void timer1_Tick(object sender, System.EventArgs e)
        {
            Point pos = Cursor.Position;
            //Cursor.Position = new Point(pos.X + 1, pos.Y + 1);
            label1.Text = Control.MousePosition.ToString();
            PreventScreenSaverFromStarting();
        }

        private void button1_Click(object sender, System.EventArgs e)
        {
            int centerX = Screen.PrimaryScreen.Bounds.Right / 2;
            int centerY = Screen.PrimaryScreen.Bounds.Bottom / 2;
            Cursor.Position = new Point(centerX, centerY);
        }

        private void PreventScreenSaverFromStarting()
        {
            INPUT input = new INPUT();
            input.type = INPUT_MOUSE;
            input.mi = new MOUSEINPUT();
            input.mi.dwExtraInfo = IntPtr.Zero;
            input.mi.dx = 0;
            input.mi.dy = 0;
            input.mi.time = 0;
            input.mi.mouseData = 0;
            input.mi.dwFlags = 0x0001; //Move (Relative)
            int cbSize = Marshal.SizeOf(typeof(INPUT));
            uint r = SendInput(1, ref input, cbSize);
        }


        #region Win32 API
        [StructLayout(LayoutKind.Sequential)]
        struct MOUSEINPUT
        {
            public int dx;
            public int dy;
            public uint mouseData;
            public uint dwFlags;
            public uint time;
            public IntPtr dwExtraInfo;
        }

        const int INPUT_MOUSE = 0;

        [StructLayout(LayoutKind.Sequential)]
        struct KEYBDINPUT
        {
            ushort wVk;
            ushort wScan;
            uint dwFlags;
            uint time;
            IntPtr dwExtraInfo;
        }

        [StructLayout(LayoutKind.Sequential)]
        struct HARDWAREINPUT
        {
            uint uMsg;
            ushort wParamL;
            ushort wParamH;
        }

        [StructLayout(LayoutKind.Explicit)]
        struct INPUT
        {
            [FieldOffset(0)]
            public int type;
            [FieldOffset(4)]
            public MOUSEINPUT mi;
            [FieldOffset(4)]
            public KEYBDINPUT ki;
            [FieldOffset(4)]
            public HARDWAREINPUT hi;
        }

        [DllImport("user32.dll", SetLastError = true)]
        static extern uint SendInput(uint nInputs, ref INPUT pInputs, int cbSize);

        [FlagsAttribute]
        public enum EXECUTION_STATE : uint
        {
            ES_SYSTEM_REQUIRED = 0x00000001,
            ES_DISPLAY_REQUIRED = 0x00000002,
            ES_CONTINUOUS = 0x80000000,
        }

        [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        static extern EXECUTION_STATE SetThreadExecutionState(EXECUTION_STATE esFlags);
        #endregion
    }
}

メモ帳でソースコード(ScreenSaverKiller.cs)をコピペし、適当な場所に保存。そしてコマンドプロンプトcscを使ってコンパイルすれば、exeファイルが出来上がります。コンパイルが通らなかったらすみません。私の環境では一応動いてます。これで5分おきにマウスを動かさなくても良いですね!

f:id:tranche:20180702095622p:plain
スクリーンショット

node.js+Puppeteerによる動的ページのスクレイピング

最近のかっこいいWebとかだと、どういう仕組みかは分からないけど動的にデータが作られていて、htmlソースを見てもスクレイピングできないことがよくある。
西友のお墨付きブランドのページも、なかなか洗練されている(DeNAが作ったらしい?)。だけど商品情報をスクレイピングしようとしても、ソースコードには何も書いてないから、僕が得意な普通のVBAではうまくいかない。
西友 - プライベートブランド みなさまのお墨付き | SEIYU

あれこれ悩んで数か月、ようやく解決方法が見つかった。Puppeteerという、node.jsで動かせるChromeのヘッドレスブラウザを使うといい。これはすごくて、スクレイピング以外にもスクリーンショットなども取れる。
対象ページから抽出したいタグは、普通のChromeでInspectを選ぶことで見られると思う。node.jsはよく分からなかったけど、見よう見まねでDQNコードを作って一応動いている。非同期のところが癖があって難しかった。
はじめの一歩だから、多分すっごく汚いコードなんだろうけど、何個か作りながらnode.jsのこととかちゃんと理解できたらいいなと思う。

node.jsの最新バージョン(async対応)と、puppeteerが必要
node script.jsで実行


script.js

const fs = require('fs');
const assert = require('assert');
const puppeteer = require('puppeteer');

const len = 1500;
const sequential = new Array(len)
    .fill(1)
    .map((n, i) => n + i);
console.log(sequential.join(','));

loop(sequential);

async function loop(v) {
	for (let n of v) {
		await hoge(n);
	}
}

async function hoge(n){
	const browser = await puppeteer.launch();
	const page = await browser.newPage();
	await page.goto('http://●●.●●●●●.●●.jp/#item_' + n);
	console.log('http://●●.●●●●●.●●.jp/#item_' + n)
	//await page.screenshot({path: 'example.png'});

	const Names = await page.evaluate(() => {
		var array = [];
		var el = document.querySelector('div.bdr')
	        var node = el.querySelectorAll("p.name, p.price, p.area, div.dsc, div.rating");
		for(item of node){
	        	array.push(item.innerText);
	        }
	        return array;
	});
	browser.close();
	//assert(fs.existsSync('example.png'));
	fs.appendFile('writetest.txt', n + ',' + replaceElement(Names) + '\n', function (err) {
	    //console.log(err);
	});
}

function replaceElement(array) {
  for(var i=0; i<array.length; i++){
    array[i] = array[i].replace(/\r?\n/g,"");
  }
  return array;
}

俺の語彙数は推定8,000語だって

WeblioとTest your vocabの両方で試してみた。
Test you vocabだと7,810語。Weblioの方は何度やってもLevel 13~14(7001語~8000語 :特待生)で止まるから、結果は概ね正しいのだろう。Guessで回答しているのもあるし。これはネイティブの小学生低学年レベルといわれている。

ということは5年前に取った英検一級は殆どまぐれだったということになる(はっきりいって語彙パートは勘で5割くらい取れてしまう試験だった)。MBA留学していてこの語彙数はちょっと少ないよな。これまでずっと単語はないがしろにしてきたけど、本を読むのに時間がかかるとか知的な文章が書けなかったりして、最近すごい弊害を感じている。

年末までにボキャビルを少し頑張ってみようと思う。

testyourvocab.com
どのレベルの語彙まで覚えるべきか?

(ご利用条件)当ブログは筆者の個人的見解を述べたものであり、筆者の所属する団体またはその公式見解とは一切関係がありません。当ブログは特定の金融商品の売買を推奨または勧誘またはあっせんするものではありません。当ブログにおいて情報提供の対価として閲覧者から金銭を徴収することはありません。当ブログの内容の正確性に関しては万全を期していますが、筆者は何らその保証を行うものではありません。投資は自己責任です。当ブログの内容をもとにして生じた損害について、筆者は一切の責任を負いません。