2022年12月5日月曜日

vbaで英字or空白を含む文字列かを判定する方法

vbaで英字か空白を含む文字列であるか否かを判定するコードを考えてみた。

Function IsAlphabet(str As String) As Boolean  
  Dim objReg As Object
  Set objReg = CreateObject("VBScript.REgExp")
  objReg.IgnoreCase = True '大文字と小文字を区別しない
  objReg.Pattern ="^[a-zA-Z a-zAZ ]+$
  IsAlphabet = objREg.test(str) '英字か空白ならばTrue そうでなければFalse
  Set objReg = Nothing
End Fuction
或いは、以下のコード。
Function IsAlpha(str as String) As boolean
  If str ="" then
    IsAlpha = False
    Exit Fuction
  End if
  IsAlpha = Not str Like"*[!a-zA-Z a-zAZ ]*"
End Function  
で、これを何に使うのかというと、例えば、名前に英字が使われていれば、外国人の名前か否かの判定に使える。
ま、パーフェクトではないが、大体それでOKといういう場合に使える。完璧を求めると、大変なので、これぐらいで手を打とうという時に使う。

2022年12月1日木曜日

vbaでInStrでは1回で市川市を抽出できないが、InStrRevならば抽出できる。

 vbaでInStr(住所を示す文字列,"市")では、前から検索のため、市川市を抽出できない。ところが、InStrRevならば、後ろから検索なので、市川市を抽出できる。つまり、前から攻めて駄目(InStr)ならば、後ろから攻めろ(InStrRev)ってことだね。

Function AREA(address as String) as String
  If inStrRev(address,"市")>0 then
    AREA = Left(address,InstrRev(address,"市"))
  End If
End function
 最初は、以下のコードで市川市を特異点として特別に扱うこと(2段構造)で回避してたんだけど、InStrRevなら1回で済ませることができる。ググってみて分かった。皆さん、凄いね。賢い人がいるんですな。ちなみに、市川市の他に市原市も同じ罠にハマるけど、InStrRevならば、大丈夫。名前に市という文字を含む場合にはInStrRevで抽出すれば良い。
Function AREA(address as String) as String
  If inStr(address,"市川市")>0 then
    AREA = Left(address,Instr(address,"市")+2)
  ElseIf inStr(address,"市")>0 then
    AREA = Left(address,Instr(address,"市"))
  End If
End function

2022年11月22日火曜日

Excel vbaで「1004 rangeクラスのautofilterメソッドが失敗しました」と怒られ、試行錯誤で辿り着いた原因。

Range("A1").Autofilter n,Array("○","×"),xlFilterValuesでフィルターをかけた。
 そしたら、「1004 rangeクラスのautofilterメソッドが失敗しました」というエラーが出た。
 色々と試したとこと、どうやら、A列からn番目の列の領域(current region)に切れ目(空白のセル、特にタイトル行の空白ありがよくあるパターン)があるとこのエラーが出るようだ。
 このエラーを回避するためには、ブランクのセルに何らかの値を入れるといいようだ。
 例えば、少なくとも1行目のタイトル行には何らかのタイトル(項目名)を入れておく。
 ここで、突然ですが、自分へのメモ。ステーキのたれのレシピです。醤油2に対して、日本酒1、みりん1。これに、ニンニクのローストが欠かせない。付け合わせは、ポテサラかな。そして、上質な赤ワイン。パンチがあるカバネー(Cabernet)がいい。

2022年11月17日木曜日

EXCEL vbaでwhereのnoをIN+配列+joinで複数指定するのではなく、noをひとつ指定したSELECT を必要な分だけ繰り返し発行する。

 EXCEL vbaでwhereのnoをIN+配列+joinで複数指定して、SQLを1回で済ませると手っ取り早いが、SQL文の最大文字数(バッチサイズ)65536バイト以内にする必要がある。
 そこで、noをひとつ指定したSELECT を必要な分だけ繰り返し発行する。
 ActiveWorkbook.Worksheets(1)のA列にNOが入っていると仮定する。これでどうじゃろかな?

Dim i As Long
Dim noStr as String
Dim strSQL as String
Dim maxRow as Long
Dim cn As New ADODB.Connection
Dim rs As New ADODB.Recordset

Private Const PROVIDER As String = "SQLOLEDB"
Private Const DATA_SOURCE As String	= "localhost"   'サーバ名
Private Const DATABASE As String = "dbname"         'データベース名
Private Const USER_ID As String = "UID=user"        'ユーザID
Private Const PASSWORD As String = "password"       'ユーザパスワード

'SQL Server認証で接続する場合
  cn.ConnectionString	= "Provider=" & PROVIDER _
                       & ";Data Source=" & DATA_SOURCE _
                       & ";Initial Catalog=" & DATABASE _
					   & ";UID=" & USER_ID _
                       & ";PWD=" & PASSWORD
  cn.Open

  maxRow = ActiveWorkbook.Worksheets(1).Cells(Rows.Count,1).End(xlUp).Row

  For i = 2 to maxRow
    nostr = activeWorkbook.WorkSheet(1).Cells(i,1).Value  
    strSQL = SELECT * from TBL_A A inner join TBL_B B on A.[NO] B.[NO] where A.[NO] IN (" & noStr & ") AND B.[TYPE] = 1;"
    rs.Open strSQL, cn
    rs.MoveFirst
    ActiveSheet.Range("A1").CopyFromRecordset rs
    If Not rs Is Nothing Then
     If rs.State = adStateOpen Then rs.Close
     Set rs = Nothing
    End If       
  Next
  
  If Not cn Is Nothing Then
   If cn.State = adStateOpen Then cn.Close
   Set cn = Nothing
  End If
   
End Sub

2022年11月6日日曜日

EXCEL vbaでSELECT文のwhere句をIN+配列+join関数で作る。

 SELECT文のwhere句のINを複数指定する場合、INの中身を配列とjoinで作る事になる。その例をぐぐっても出てこなかったので、やむを得ず作ってみた。
 ActiveWorkbook.Worksheets(1)のA列にNOが入っていると仮定する。これでどうじゃろかな?

Dim i As Long
Dim noStr as String
Dim strSQL as String
Dim noArr as variant
Dim maxRow as Long
maxRow = ActiveWorkbook.Worksheets(1).Cells(Rows.Count,1).End(xlUp).Row
reDim noArr(maxRow)
For i = 2 to maxRow
 noArr(i-2) = Cells(i,1)  '1次元配列に入れる
Next
noStr = join(noArr,",")
strSQL = SELECT * from TBL_A A inner join TBL_B B on A.[NO] B.[NO] where A.[NO] IN (" & noStr & ") AND B.[TYPE] = 1;"

2022年11月4日金曜日

sqlのwhereでINとANDを併用してみる。

select A.NO B.NO from A inner join B on A.NO = B.NO where A.NO IN (1,2,3) AND B.TYPE = 9 ;
こう書いても良い
select A.NO B.NO from A inner join B on A.NO = B.NO where (A.NO,B.TYPE) IN ((1,9),(2,9)(3,9)) ;

vbaのjoinで一次元配列をカンマ区切りの文字列にする。

Dim myArray as variant
myArray = array(1,2,3,4,5)
myArrayStr = join ( myArray,",")   ' myArrayStr = 1,2,3,4,5

2022年10月27日木曜日

access vbaでラジオボタン(オプションボタン)を操る。

 入力フォームという名前のフォームにfrmTypeというフレームを追加し、そのフレームに「type1(値1)」と「type2(値2)」というオプションボタンを追加した。
 標準モジュールで、オプションボタンを判定するコードは、以下のような感じだ。

  If [Forms]![入力フォーム]![frmType].Value = 1 then
  [type1の処理]
  else
  [type2の処理]
  End If

2022年10月20日木曜日

access vbaで最適化コマンドは開いていると実行できないので、起動パラメタで制御できるようにしてみた。確実に。

 access vbaでは、最適化コマンドはdbを開いていると実行できない。
 SendKeys "%(YC)"またはSendKeys "%(Y){TAB}{Enter}"で動かせるようだが、SendKeysはキー送信のため、不安定であり、うまく動かないことがある。
 確実に最適化を動かすために、起動パラメタを使うのがいい。是非、マネしてください。
起動パラメタは、c:¥Users¥username¥Documents¥abc.accdb /cmd "actParam1"というコマンドラインを叩くと、起動時にactParam1というパラメタをvbaで受け取ることができる。
一方、accessの設定で、閉じると自動的に最適化を行うようにしておく。
 以下のモジュールをvbaで書いて、AutoExecという名前のマクロを作成し、AutoStartProcプロシジャを開くように登録しておく。
AutoStartProcの中身は、こんな感じだ。

Public Function AutoStartProc()
  If InStr(Command,"actParam1")>0 then 
    Application.Quit  ’オプションの□ 閉じると最適化するにチェックを入れておく。この結果、最適化が走る。 
  ElseIf InStr(Command,"actParam2")>0 then
    [最適化後にやりたい処理]
    Docmd.XXXXX
    Docmd.YYYYY
    Aoplication.Quit
  End If
End Function
 これで、actParam1という起動パラメタの場合、accessを閉じる(Application.quit)ことで最適化が走るようになる仕掛けが完成する。
 そして、start /wait c:¥Users¥username¥Documents¥abc.accdb /cmd "actParam1"で起動すれば、最適化が動く。なお、/waitにより、必ずコマンドの完了を待つことができる。そして、これ(/wait)がとても大切になる。また、不要なオブジェクト、つまり、2GB超えの要因となりそうなテーブルを再作成するケースであれば、再作成の前にこのタイミングで、いったん全てのオブジェクトを一旦、削除して、最適化を走らせておくのがよろしいだろう。
 また、start /wait c:¥Users¥username¥Documents¥abc.accdb /cmd "actParam2"で起動すれば、actParam2のアクションを行うことができる。

2022年10月14日金曜日

accessでパラメタ付きのクエリーをvbaで操作するには、そのパラメタをフォームに変更するしかないのかもしれない。

accessでパラメタ付きのクエリーをvbaで操作するには、そのパラメタをフォームに変更するしかないのかもしれない。
つまり、vbaでパラメタに値を設定するのはできないのかもしれない。パラメタをフォームにすれば、vbaで値を設定するのは、簡単だ。

2022年9月21日水曜日

EXCEL vbaでラジオボタン(オプションボタン)を操る。

EXCEL vbaでラジオボタン(オプションボタン)を操る。 menuシートのActiveXで作成した ◉ OptionButton1 ボタンの状態を判定するコードは、こんな感じだ。

  If Worksheets("menu").OptionButton1.Value = False then exit sub
menuシートのフォーム・コントロール(FormControl)で作成した ◉ OptionButton1 ボタンの状態を判定するコードは、以下の通りだ。
  If Worksheets("menu").OptionButtons("Option Button 1").Value = 1 then exit sub
ActiveXの場合、ラジオボタンのオン・オフは、trueかfalseで判定する。
一方、フォーム・コントロールの場合、オプションボタン(ラジオボタン)のオンは、値が1かで判定する。オフは、なんと、値が-4142かで判定する。面白すぎるので、注意が必要だ。似ているようで違うのだ。罠にハマらないようにしたい。以上のことは、ぐぐった末にコードを動かして、わかったのだけれど、マイクロソフトのどこかのドキュメントにはあるんだろうね。どこかは知らんけど。

2022年9月14日水曜日

vbaのdirが動かないと思ったら¥が漏れていたことに気がつくまでにかなり時間がかかった話。myPathのあとには必ず¥がいるんだな。

vbaで以下のコードを書いた。

Dir myPath As String
Dim fileName As String
myPath = thisworkbook.path
fileName = "ABC.xlsx"
if dir(MyPath & fileName) <> "" then kill Mypath & fileName
dir(myPath & fileName)の結果がいつも””となり、dirがバグってると思った。 しかし、原因は、myPathとfileNmeの間にディレクトリの切れ目の¥がなかったため、正しくファイルを見つけられないためだった。 dir(mypath & "¥" & fileName)であれば、OKだった。myPathのあとには必ず¥がいるんだな。エンサインだよ。あるいは、バックスラッシュだよ。必要だよ。 vbaを書くと時間が潰れる。

2022年9月6日火曜日

accessが2GBを超えた時のメッセージは、「データベースを開くことができません。アプリケーションで認識できないデータベースであるか、またはファイルが破損しています。」だったので、すぐに原因がわからなかった。

accessが2GBを超えた時のメッセージは、「データベースを開くことができません。アプリケーションで認識できないデータベースであるか、またはファイルが破損しています。」だったので、すぐに原因がわからなかった。

2022年8月31日水曜日

全銀フォーマットのカナには拗音(ようおん)がないが、口座カナ名には使いたい。

では、どうするかというと、全銀システムに渡すデータでは、拗音を使わず、それ以外では、拗音を許容すれば良い。

2022年8月26日金曜日

accessのフォームにラジオボタンを作り、そのボタンのオン・オフで、その後の処理を変更するコードをvbaで書いてみた。

まず、accessのフォーム(入力フォームという名前とする)のデザイン画面で、ラジオボタン(目玉みたいなボタン)として、バナナという名前のボタンを追加し、規定値(初期値)はtrueまたはFalseにしておく。 次に、そのラジオボタンを判定(黒目があるときはオン[true]<-1>で、黒目がないときはオフ[False]<0>)し、処理を振り分けるコードをvbaで書いてみた。
ググっても、こういう使い方を説明しているサイトが見当たらなかった。当たり前すぎるのかなぁ。
     If [forms]![入力フォーム]![バナナ] = True then  'バナナボタンがオンの場合の処理を書く。
       MsgBox "バナナボタンがonやで"
       Debug.print "バナナボタンがonやで"
     else
       'バナナボタンがオフの場合の処理を書く。
       MsgBox "バナナボタンがoffやで"
       Debug.print "バナナボタンがoffやで"
     End If

2022年8月24日水曜日

excel vbaでセルの値がmm 月dd日と表示されてしまうのを回避した

EXCELの書式自動設定のおかげで、あるセルの値がmm月dd日と表示されて、実に困った。過剰で、お節介な機能で、しかもどういう条件で起こるか、わからない。excelはおせっかいな奴だ。
そこで、仕方がないので、vbaでセルに値を設定した直後に、.NumberForamtLocal = "G/標準”で書式を強制的に入れるようにして、回避したのであった。やれやれ。

2022年8月19日金曜日

accessのテーブルを固定長テキストファイルにエクスポートするのにDocmd.transfertextではなく、print(vba)を使ったというお話。

DoCmd.TransferTextでacExportFixedを指定してのテキスト出力すると、「specification name/定義名が必要です」とか言われて、面倒くさいので、テーブルの内容をprintするvbaを書いてみた。
adoでもdaoでもどちらでも良いので、参照設定で、ライブラリを設定し、テーブルの内容を1個ずつ、printで吐き出せば良い。これだけだ。
specificationNameに悩まされることもなく、テキストファイルが得られる。accessのtblAがフィールドが1つのテーブルであったと仮定し、DAOで書くと

Sub ExportText()
  Dim dbs as Database '参照設定でDAOを設定せよ
  Dim rs  as RecordSet
  Dim IngFileNum as Long
  Dim strOutPut as String
  Dim path1 as String
  Dim file1 as String
  path1 = CurrentProject.path & "¥OUTPUT¥"
  file1 = "tblA.txt"
  IngFileNum = FreeFile()
  Open path1 & file1 For OutPut As #IngFileNum
  Set dbs = CurrentDb
  Set rst = dbs.OpenRecordset("tblA") 
  With rst
    do Until .EOF
      print #IngFileNum,rst(0) &  vbCrLf; 'tblAにはフィールドが1つ
      .MoveNext
    Loop
    .Close
  End With
  Close #IngFileNum
End Sub

2022年8月18日木曜日

accessのテーブルを固定長のテキストファイルにエクスポートしようとして、七転八倒し、学んだこと。

expression.TransferText (TransferType, SpecificationName, TableName, FileName, HasFieldNames, HTMLTableName, CodePage)
expression A variable that represents a DoCmd object.
DoCmd.TransferText acExportFixed, "specNameA", _ 
    "tableA", "C:\Txtfiles\April.txt"
DoCmd.TransferTextでacExportFixedを指定してのテキスト出力すると、「specification name/定義名が必要です」と怒られる。
そこで、エクスポートウィザードの操作を保存したものを指定しても「定義名が見つからない」と再び、怒られる。
そもそもこの「specification name/定義名」は、エクスポートウィザードの操作を保存した名前ではないのである。
エクスポートウィザードの操作を実施したあとに出てくる、保存しますかのチェックボックスをチェック印をつけておかないと駄目なのである。
そうすると、定義というボタンが出現するのだ。ここで、specification name/定義名を定義できるのである。そして、この定義名をspecification nameに指定するのである。
ポイントは、specification name/定義名は、エクスポートウィザードの操作を保存した名前ではないということだ。
しかも、エクスポートウィザードの延長で、保存した名前と「specification name/定義名」が似ているので、余計に惑わされるのである。

2022年8月16日火曜日

accessのクエリでテキストを抽出条件とする場合、例えば1 でないものを抽出する条件は<>"1"だが、nullも忘れるな

accessのクエリでテキストを抽出条件とする場合、例えば1でないものを抽出する条件は<>"1"だが、or nullも忘れるな

2022年7月22日金曜日

vba/excelの桁数制限下での左(前方)0詰めと右(後方)半角空白詰めのひとつの手法

vbaの4桁右ゼロ詰めは、Format(key1,"0000")
EXCELシートのAnセルの内容を4桁左(前方)ゼロ詰めする場合、=TEXT(An,"0000")の関数を埋め込む。
vbaの40桁右(後方)半角空白詰めは、Left(key2 & String(40," "),40)

2022年7月14日木曜日

vbaで最大行を求めるにはxldownよりもxlupを使うのが良さそうだ。これをVBA SNIPPETSにする。

Cells(1, 1).End(xlDown).Rowではなく、Cells(Rows.Count, 1).End(xlUp).Rowの方が良さそうだ。

'Snippets for VBA
'Get maxRow and maxClm
  Dim maxRow As Long
  maxRow = Cells(Rows.Count, 1).End(xlUp).Row 'the last Row of column A
  maxClm = Cells(1, Columns.Count).End(xlToLeft).Column 'max Column of row 1

2022年7月6日水曜日

mk editorはEUCかシフトJISか判定できない時に「ShiftJISまたはEUCで文字列を識別できませんでした。EUCとして開いて問いでしょうか?[はい]EUCとして開く[いいえ]ShiftJISで開くというメッセージを出す。

mk editorはEUCかシフトJISか判定できない時に「ShiftJISまたはEUCで文字列を識別できませんでした。EUCとして開いてよいでしょうか?[はい]EUCとして開く[いいえ]ShiftJISで開くというメッセージを出す。

2022年6月21日火曜日

accessでexcelを取り込む際に1行目(タイトル行)が破壊されてもインポートできるようにするまでの物語

 accessのテーブルにexcelを取り込むのに、1行目(タイトル行)が破壊されてもインポートできるようにするため、2行目からインポートする。
 すると、取り込み先のテーブルが新規テーブルであれば、自動的にテーブルのフィールド名がF1,F2,F3・・・・となる。
 取り込み先のテーブルが新規テーブルではなく、既存テーブルの場合、テーブルのフィールド名がF1,F2,F3・・・・となっていなけレバならない。
 そうでない場合には、F1フィールドがありませんというエラーメッセージでインポートが失敗する。
 そこで、既存テーブルがある場合には、いったん、削除しておくという奥の手を使うこともできる。

  Docmd.DeleteObject acTable,"table1"
 そして、フィールド名がF1,F2,F3・・・・のままでは、具合が悪い(使い勝手が悪い)ので、
 以下のvbaコードでフィールド名を自分の好きな名前に一括変更してみた。これで、うまく行くことを祈る。
 Sub FieldNameChange()
  Dim dbs As Database
  Set dbs = CurrentDb
  With dbs.TableDefs("table1")
    .Fields("F1").Name = "番号"
    .Fields("F2").Name = "名前"
    .Fields("F3").Name = "年齢"
    (繰返し)
    .Fields.Refresh
  End With
End Sub

2022年6月13日月曜日

vbaでのテキストフィルターのワイルドカードについての考察

 vbaの.autoFilterでテキストフィルタをかける場合、ワイルドカードの指定をすることが多々ある。後方一致としての○○*とするのは、問題ないが、前方一致の*○○が問題である。 *○○とは、○○が1文字目からとなっているものが抽出できないようだ。2文字目から〇〇となっているものならば、抽出できる。つまり、1文字目に何かの文字がないと、検出できない。仕様通りといえば、そうかもだが・・・

2022年6月11日土曜日

Visual Studio Codeでテキスト文書をわざわざマークダウン(markdown)記法で書く理由

 Visual Studio Codeでテキスト文書をマークダウン(markdown)記法で書いて、プラグインでpdfとして表示(ただし、visual studio codeにmarkdownと認識させるため、ファイル拡張子を.mdにする必要がある)してみた。
 ところが、字下げ(インデント)ができないことが判明した。それは、日本語の仕様書として、具合が悪いと思った。
 でも、&nbsp;で半角空白になることがわかり、プラグインモジュールでPDF出力しても有効だったのだ。
 何故、pdfにするのに、わざわざテキスト文書をmarkdown記法で書くのか?wordかexcelで文書を作り、PDFにすれば良いのでは?と思われる方も多いことだろう。
 その理由は、テキスト文書をmarkdown記法で書くだけで、字を大きくしたり、太くしたりといった編集作業をせずに、マークダウン記法による簡単なルールで、そこそこのワンパターンだが、それなりのPDFが出来てしまうからだ。一応、仕様書としての体裁を整えるに実に都合が良いのである。しかも、テキスト文書を作りながら、プレビューで出来栄えを確認できるので、これまた、都合がよろしいのだ。

2022年6月7日火曜日

vbaでpdf出力したら、保存できませんでしたと怒られたのは、指定したフォルダ名が間違えていたためと気がつくまでの物語

 vbaでpdf出力したら、保存できませんでしたと怒られた.
その原因は、pdf出力先のフォルダを作成していなかったため(正確に言えば、フォルダ名を間違えていたため)だが、「ファイルが保存できませんでした」という不親切なメッセージでは気がつくのに物凄く時間がかかったのだった。
でも一番悪いのは、自分。もっと足元を見ろということですね。間違えているのは、自分だよってことだね。

Dim file1 as string
Dim filePath as string
' C:¥Users¥user1¥documents¥pdf¥output
filePath = Thisworkbook.Worksheets("menu").Range("B5").Value  
file1 = filePath & test.pdf"
ActiveSheet.ExportAsFixedFormat Type:=xlTypePDF, Filename:=file1

2022年5月31日火曜日

vbaでexcelを保存しても書式が引き継がれないというトラブルを解決するまでの物語

Dim wb as workbook
Sub tool()
  Set wb = Activeworkbook
  wb.save
End

 vbaで金額が¥-nnn,nnnと表示されるように書式を設定して、ツールを作った。コードの最後でwb.saveしている。ところが、そのセーブしたツール(.xlsm)を開くと、見事に書式が引き継がれないというトラブルに遭遇した。saveすると、書式がぶっ飛ぶようだ。解決策は、saveしないことだ。或いは、saveas フルパスのファイル名,local:=Trueに変えれば良い。通常、これを人はバグと呼ぶ。マイクロソフトはどうなんだろうか?

2022年5月26日木曜日

値の合計はSUMIFSで、個数はCOUNTIFSで集計すればいい。vbaでコードを書く必要はない。

集計するためにvbaでコードを書く必要は必ずしもない。埋め込み関数で、値の合計はSUMIFSで、個数はCOUNTIFSで集計するだけでいい。vbaで集計のコードを書かなくていいんだ。ということに気がついた。

2022年5月20日金曜日

みそ汁の出汁がらのいりこで作る佃煮のレシピ〜世界で一番簡単なレシピ

 我が家では、みそ汁の出汁をとったあとのいりこを冷凍して置く。ある程度、溜まったら、いりこの佃煮にする。鍋に出汁がらのいりこ100g、砂糖大さじ2、みりん大さじ2、醤油大さじ2、酢大さじ1、しょうがすり潰し少々、赤唐辛子少々をいれ、汁気がなくなるまで煮詰める。最後に白胡麻を振れば、佃煮になる。このレシピは、2代目。

2022年5月15日日曜日

世界一簡単なもち粉パンケーキのレシピ

  • 卵 1個 + 塩 2.5グラム(小さじ半分)+ 砂糖 18グラム(大さじ2)をボールに入れて、泡立る。
  • 牛乳 100グラム(cc)+もち粉100グラム+ベーキングパウダー5グラム(小さじ1)+オリーブオイル14グラム(大さじ1)を混ぜる。
  • フライパンに大さじ1〜2の量をたらし、焼く。表面がふつふつし、泡が弾けたら、ひっくり返し、焼く。 もち粉100%だと、モチモチしすぎるので、焼くのが難しい。半分、米粉や小麦粉にする方が良いかも。

2022年5月13日金曜日

一冊の本(2008年3月号)

 ここに「一冊の本」という名前の本(2008年3月号)がある。その中におつかいナプキンという宮田珠己(みやた たまき)のエッセイがある。単行本になっていたと思うが、タイトルは失念した。頒布100円と書いてあるが、本屋さんで無料で貰ったものだ。面白いもの(本)との出会いは、或る日、突然、訪れる。

2022年4月17日日曜日

gentooのpython 2.7 でopen-tsukubaiのsm2を動かす

 gentooの端末のコマンドラインで
python2.7 /usr/local/bin/sm2 1 2 4 8 data1
と打つと、
0001 新橋店 219 98 51 165 85
0002 池袋店 166 134 135 74 87
0003 新宿店 184 172 93 45 142
0004 上野店 247 205 151 207 157

markdownという記述方法で、テキストベースの文書を書くと、製本イメージの文書作成ができる。
 マイクロソフトのVisual Studio Codeで、プレビューすることができる。いいんじゃないの?

2022年3月30日水曜日

accessのクエリがODBCタイムアウトで失敗することがあるので、タイムアウト時間を大きくしてみた。

doc-anzai
 accessのクエリがODBCタイムアウトで失敗することがある。 対応として、ODBCタイムアウト時間をデフォルトの60(秒)から180にしてみた。 
 やり方は、クエリをデザインビューで開き、何もない列で右クリックし、クエリのプロパティを表示させる。  そして、ODBCタイムアウトの箇所を60から180へ変更し、クエリを保存するだけだ。
 
 3年前、まだ世の中にコロナがなかった頃にイタリアへ旅行しようと思い立ち、インターネットでホテルと航空券を検索し、色々とプランを練ったことがあった。結局、夢が萎んで、プランが完成せずに、イタリアには行かなかった。しかし、あまりに検索したせいで、もう、そこへ出かけたかのような気分になれたのだった。大聖堂を歩き、夜の街を彷徨い、食事を楽しんだ。ワインを飲み、ピザを堪能した。タクシーに乗り、旅行カバンを抱えた。あの時、完全に海外にいたなぁ。ホテルは、どんな内装で、
ロフトがあり、近くには、素敵なカフェがあった。


 

2022年3月16日水曜日

vbaでシート保護をかけたら、マクロが動かなくなったのをリカバるまでのストーリー


 
zonbi-girl-202204
zonbi-girl-202204
vbaの.protect userinterfaceonly:=true(マクロだけはシート保護されても動くおまじない)でシート保護をかけたら、マクロが動かなくなった。  その理由は、userinterfaceonlyのおまじないは、ファイルをオープンする度に唱えないと駄目(ファイルを保存すると消える)という冗談みたいなマイクロソフトの仕様による。 
 またもや、しようもない仕様に翻弄されたワタシ。マクロで、シート保護のコードを書いた後にはちゃんとテストしましたよ。でも、保存した後にはもう一度テストしないと動かないことがわからないなんて、わかるわけがないですね。なんか変なこと言ってますかね?
 シート保護しで、フィルターはできるようになったけど、オートフィルターを外すことはできないので、使い勝手が悪い。シート保護とオートフィルターの両立はイマイチだね。保護かフィルターかは相反するんだね。
 

 


2022年3月11日金曜日

accessで全く同じフィールド(ユニークキーあり)を持つ、2つのテーブルに対し、どちらか片方に片寄せ(キーがないものは追加、キーがあるものは更新)する

 accessで全く同じフィールド(ユニークキーあり)を持つ、2つのテーブルに対し、どちらか片方に片寄せ(キーがないものは追加、キーがあるものは更新)するには、  まず、2つのテーブルの差分(同じキーがないもの)を差分抽出クエリで生成し、追加する。同じキーがあれば、UPDATEで全てのフィールド(1行)を更新すればよい。

 先日、IPS細胞の山中伸弥さんが「植物は万能細胞」という話をされていたを聞いて、思い出した。昨年、ベランダ菜園の唐辛子の茎を誤って切ってしまったときの話だ。そんまま、さしておいたら、見事に根が再生し、すくすく成長し、立派に唐辛子の実を付けたのだった。すごいね、万能細胞の植物、再生力が強い。

2022年2月18日金曜日

accessのクエリでパーセントを表示するには、Format([ 式],"0.0%")でいい。

 accessのクエリでパーセントを表示するには、Format([式],"0.0%")でいい。式にフィrールド名(必要ならテーブル名!を付ける)を書けばいい。

carrot


2022年2月8日火曜日

accessのフォームのテキストボックスに更新後処理のイベントプロシジャを設定する。

accessのフォームのテキストボックスに更新後処理のイベントプロシジャを設定する。

Private Sub 当月_AfterUpdate()
  With Me!当月
    msgBox Me!当月
  End With
end sub

2022年2月6日日曜日

access にexcelファイルの特定列をインポートするvbaコードを書いてみた。

access にexcelファイルの特定列(例えば、シート名が顧客リストのセルA2からc列まで)を顧客リストというテーブルにインポートするvbaコードを書いてみた。

Sub ImportExcel()
Dim file1 as String
  file1 = "C:¥Users¥username¥Documents¥importedEXCEL.xlsx"
  if DCount("*", "MSysObjects", "[Name] = '顧客リスト'") > 0 Then DoCmd.DeleteObject acTable,"顧客リスト"  ' 顧客リストがあれば削除する
  DoCmd.TransferSpreadsheet acImport,acSpreadsheetTypeExcel12Xml,"顧客リスト",file1,True,顧客リスト!A2:C
End Sub

2022年1月29日土曜日

accessでexcelファイルを取り込むにはインポート(acImport)か、リンク(acLink)か、どっちがよろしいのか?比べて、自動化のコードをvbaで書いてみた。

 accessでexcelファイルを取り込むのにインポートが良いのか、或いはリンクが良いのか?

 元のファイルを明確にする(しておきたい)必要がある場合は、リンク(acLink)を使うのが良い。
 accessを開いた状態では、リンクしているexcelファイルがロックされるので、他のユーザがexcelファイルを更新できない(読み取り専用となる)。
 勿論、accessを閉じれば、いいだけだ(他のユーザはexcelファイルを更新できるようになる)。
 そんな使い勝手は、窮屈で嫌だというのであれば、元ファイルをその度にコピーし、複製をリンクしておくのがよろしいのではないか。
 リンクした場合、データの型変換エラーがあると、そのフィールドが#num errorと表示されるが、実際、その値が使用されるまでわからない(と思う)。
 また、リンクしたテーブルが空(タイトル行のみで、データ行がない)の場合、そのテーブルを参照するクエリは、全て型エラーになる(タイトル行のみで、データがないため、データ型を決められない=型が一致しないというチグハグなエラーで怒られる)ので、テーブルが空、つまり、タイトル行しかない場合は、そのクエリをスキップするとかの対応が必要となる。 vbaで書くと、If dcount("フィールド名","テーブル名") > 0 で判定し、成立した場合にクエリを出すというのがよろしい。
 excelファイルをリンクするvbaを書いてみた。これでリンク操作を自動化できる。

Sub ImportExcel()
Dim file1 as String
  file1 = "C:¥Users¥username¥Documents¥importedEXCEL.xlsx"
  if DCount("*", "MSysObjects", "[Name] = 'テーブル1'") > 0 Then DoCmd.DeleteObject acTable,"テーブル1"  ' テーブル1があれば削除する
  DoCmd.TransferSpreadsheet acLink,acSpreadsheetTypeExcel12Xml,"テーブル1",file1,True,シート名
  If Dcount("フィールド1","テーブル1") > 0 then 'テーブル1が空でなければ(フィールド1のデータが存在する)、クエリ1を実行する
    DoCmd.Query "クエリ1"
  End if
End Sub

 元のファイルを明確にする必要がなければ、インポート(acImport)を使うのが良い。
 インポートを使えば、元のexcelファイルがロックされることはない。  インポートを使うと、型変換エラーがあったら、インポート直後にその旨のエラーメッセージが出るので、対応しやすい。ただし、エラーを見逃さない執念深さが必要である。
 excelファイルのインポート操作を自動化するvbaは、以下の通りだ。
Sub ImportExcel()
Dim file1 as String
  file1 = "C:¥Users¥username¥Documents¥importedEXCEL.xlsx"
  if DCount("*", "MSysObjects", "[Name] = 'テーブル1'") > 0 Then DoCmd.DeleteObject acTable,"テーブル1"  ' テーブル1があれば削除する
  DoCmd.TransferSpreadsheet acImport,acSpreadsheetTypeExcel12Xml,"テーブル1",file1,True,シート名
End Sub

2022年1月18日火曜日

access vba excel基本のコード

 access vba excel操作の基本のコードは、以下の通り。
 とりあえず、excel文書をオープンし、Sheet1を削除、上書き保存するコードを書いてみた。

Dim exApp As Object
Dim Wb As Object
Dim buf As string
    Set exApp = CreateObject("Excel.Application")
   exApp.Visible = False
   exApp.DisplayAlerts = False
   Set Wb = ExApp.Workbooks.Open("¥¥dir1¥dir2¥filename.xlsx")
   or
   buf = "¥¥dir1¥dir2"
   file1 = dir(buf & "filename.xlsx")
   exApp.workbooks(file1).open file1
  With Wb
    .Worksheets("Sheet1").Delete
       other codes
    .Save
    .Close
  End With
  exApp.DisplayAlerts = True
  exApp.Quit
   Set exApp = Nothing

2022年1月12日水曜日

excelの複数シートコピーで、他シートへのリンクがあるシートは、参照元と参照先のシートを指定し、同時にコピーしなけばならない。

excelの複数のシートコピーで、他シートを参照するリンクがあるシートは、参照元と参照先のシートをarray指定し、同時にコピーしなけばならない。そうしないと、元々のファイルへの外部参照のリンクができてしまい、都合が悪具なる。